4 -----------------------------------
5 WADEDITOR.PAS ÂÅÐÑÈß ÎÒ 26.08.08
7 Ïîääåðæêà âàäîâ âåðñèè 1
8 -----------------------------------
16 SArray
= array of ShortString;
18 TWADEditor_1
= class(TObject
)
21 FResTable
: packed array of TResourceTableRec_1
;
22 FHeader
: TWADHeaderRec_1
;
29 function LastErrorString(): string;
30 function GetResName(ResName
: string): Char16
;
33 destructor Destroy(); override;
35 function ReadFile(FileName
: string): Boolean;
36 function ReadMemory(Data
: Pointer; Len
: LongWord): Boolean;
37 function HaveResource(Section
, Resource
: string): Boolean;
38 function HaveSection(Section
: string): Boolean;
39 function GetResource(Section
, Resource
: string; var pData
: Pointer;
40 var Len
: Integer): Boolean;
41 function GetSectionList(): SArray
;
42 function GetResourcesList(Section
: string): SArray
;
44 property GetLastError
: Integer read FLastError
;
45 property GetLastErrorStr
: string read LastErrorString
;
46 property GetResourcesCount
: Word read FHeader
.RecordsCount
;
47 property GetVersion
: Byte read FVersion
;
52 DFWAD_ERROR_WADNOTFOUND
= -1;
53 DFWAD_ERROR_CANTOPENWAD
= -2;
54 DFWAD_ERROR_RESOURCENOTFOUND
= -3;
55 DFWAD_ERROR_FILENOTWAD
= -4;
56 DFWAD_ERROR_WADNOTLOADED
= -5;
57 DFWAD_ERROR_READRESOURCE
= -6;
58 DFWAD_ERROR_READWAD
= -7;
59 DFWAD_ERROR_WRONGVERSION
= -8;
62 procedure g_ProcessResourceStr(ResourceStr
: String; var FileName
,
63 SectionName
, ResourceName
: String); overload
;
64 procedure g_ProcessResourceStr(ResourceStr
: String; FileName
,
65 SectionName
, ResourceName
: PString); overload
;
70 SysUtils
, BinEditor
, ZLib
;
73 DFWAD_OPENED_NONE
= 0;
74 DFWAD_OPENED_FILE
= 1;
75 DFWAD_OPENED_MEMORY
= 2;
77 procedure DecompressBuf(const InBuf
: Pointer; InBytes
: Integer;
78 OutEstimate
: Integer; out OutBuf
: Pointer; out OutBytes
: Integer);
84 FillChar(strm
, sizeof(strm
), 0);
85 BufInc
:= (InBytes
+ 255) and not 255;
86 if OutEstimate
= 0 then
89 OutBytes
:= OutEstimate
;
90 GetMem(OutBuf
, OutBytes
);
92 strm
.next_in
:= InBuf
;
93 strm
.avail_in
:= InBytes
;
94 strm
.next_out
:= OutBuf
;
95 strm
.avail_out
:= OutBytes
;
96 inflateInit_(strm
, zlib_version
, sizeof(strm
));
98 while inflate(strm
, Z_FINISH
) <> Z_STREAM_END
do
101 Inc(OutBytes
, BufInc
);
102 ReallocMem(OutBuf
, OutBytes
);
103 strm
.next_out
:= PByteF(PChar(OutBuf
) + (PChar(strm
.next_out
) - PChar(P
)));
104 strm
.avail_out
:= BufInc
;
109 ReallocMem(OutBuf
, strm
.total_out
);
110 OutBytes
:= strm
.total_out
;
117 procedure g_ProcessResourceStr(ResourceStr
: String; var FileName
,
118 SectionName
, ResourceName
: String);
123 for i
:= Length(ResourceStr
) downto 1 do
124 if ResourceStr
[i
] = ':' then
127 FileName
:= Copy(ResourceStr
, 1, i
-1);
129 for a
:= i
+1 to Length(ResourceStr
) do
130 if (ResourceStr
[a
] = '\') or (ResourceStr
[a
] = '/') then Break
;
132 ResourceName
:= Copy(ResourceStr
, a
+1, Length(ResourceStr
)-Abs(a
));
133 SectionName
:= Copy(ResourceStr
, i
+1, Length(ResourceStr
)-Length(ResourceName
)-Length(FileName
)-2);
136 procedure g_ProcessResourceStr(ResourceStr
: AnsiString; FileName
,
137 SectionName
, ResourceName
: PAnsiString);
139 a
, i
, l1
, l2
: Integer;
142 for i
:= Length(ResourceStr
) downto 1 do
143 if ResourceStr
[i
] = ':' then
146 if FileName
<> nil then
148 FileName
^ := Copy(ResourceStr
, 1, i
-1);
149 l1
:= Length(FileName
^);
154 for a
:= i
+1 to Length(ResourceStr
) do
155 if (ResourceStr
[a
] = '\') or (ResourceStr
[a
] = '/') then Break
;
157 if ResourceName
<> nil then
159 ResourceName
^ := Copy(ResourceStr
, a
+1, Length(ResourceStr
)-Abs(a
));
160 l2
:= Length(ResourceName
^);
165 if SectionName
<> nil then
166 SectionName
^ := Copy(ResourceStr
, i
+1, Length(ResourceStr
)-l2
-l1
-2);
172 constructor TWADEditor_1
.Create();
178 FHeader
.RecordsCount
:= 0;
180 FWADOpened
:= DFWAD_OPENED_NONE
;
181 FLastError
:= DFWAD_NOERROR
;
182 FVersion
:= DFWAD_VERSION
;
185 destructor TWADEditor_1
.Destroy();
192 procedure TWADEditor_1
.FreeWAD();
194 if FResData
<> nil then FreeMem(FResData
);
198 FHeader
.RecordsCount
:= 0;
200 FWADOpened
:= DFWAD_OPENED_NONE
;
201 FLastError
:= DFWAD_NOERROR
;
202 FVersion
:= DFWAD_VERSION
;
205 function TWADEditor_1
.GetResName(ResName
: string): Char16
;
207 ZeroMemory(@Result
[0], 16);
208 if ResName
= '' then Exit
;
210 ResName
:= Trim(UpperCase(ResName
));
211 if Length(ResName
) > 16 then SetLength(ResName
, 16);
213 CopyMemory(@Result
[0], @ResName
[1], Length(ResName
));
216 function TWADEditor_1
.HaveResource(Section
, Resource
: string): Boolean;
219 CurrentSection
: string;
223 if FResTable
= nil then Exit
;
225 CurrentSection
:= '';
226 Section
:= AnsiUpperCase(Section
);
227 Resource
:= AnsiUpperCase(Resource
);
229 for a
:= 0 to High(FResTable
) do
231 if FResTable
[a
].Length
= 0 then
233 CurrentSection
:= FResTable
[a
].ResourceName
;
237 if (FResTable
[a
].ResourceName
= Resource
) and
238 (CurrentSection
= Section
) then
246 function TWADEditor_1
.HaveSection(Section
: string): Boolean;
252 if FResTable
= nil then Exit
;
259 Section
:= AnsiUpperCase(Section
);
261 for a
:= 0 to High(FResTable
) do
262 if (FResTable
[a
].Length
= 0) and (FResTable
[a
].ResourceName
= Section
) then
269 function TWADEditor_1
.GetResource(Section
, Resource
: string;
270 var pData
: Pointer; var Len
: Integer): Boolean;
275 CurrentSection
: string;
281 CurrentSection
:= '';
283 if FWADOpened
= DFWAD_OPENED_NONE
then
285 FLastError
:= DFWAD_ERROR_WADNOTLOADED
;
289 Section
:= UpperCase(Section
);
290 Resource
:= UpperCase(Resource
);
293 for a
:= 0 to High(FResTable
) do
295 if FResTable
[a
].Length
= 0 then
297 CurrentSection
:= FResTable
[a
].ResourceName
;
301 if (FResTable
[a
].ResourceName
= Resource
) and
302 (CurrentSection
= Section
) then
311 FLastError
:= DFWAD_ERROR_RESOURCENOTFOUND
;
315 if FWADOpened
= DFWAD_OPENED_FILE
then
318 AssignFile(WADFile
, FFileName
);
321 Seek(WADFile
, FResTable
[i
].Address
+6+
322 LongWord(SizeOf(TWADHeaderRec_1
)+SizeOf(TResourceTableRec_1
)*Length(FResTable
)));
323 TempData
:= GetMemory(FResTable
[i
].Length
);
324 BlockRead(WADFile
, TempData
^, FResTable
[i
].Length
);
325 DecompressBuf(TempData
, FResTable
[i
].Length
, 0, pData
, OutBytes
);
332 FLastError
:= DFWAD_ERROR_CANTOPENWAD
;
339 TempData
:= GetMemory(FResTable
[i
].Length
);
340 CopyMemory(TempData
, Pointer(LongWord(FResData
)+FResTable
[i
].Address
+6+
341 LongWord(SizeOf(TWADHeaderRec_1
)+SizeOf(TResourceTableRec_1
)*Length(FResTable
))),
342 FResTable
[i
].Length
);
343 DecompressBuf(TempData
, FResTable
[i
].Length
, 0, pData
, OutBytes
);
349 FLastError
:= DFWAD_NOERROR
;
353 function TWADEditor_1
.GetResourcesList(Section
: string): SArray
;
356 CurrentSection
: Char16
;
360 if FResTable
= nil then Exit
;
361 if Length(Section
) > 16 then Exit
;
363 CurrentSection
:= '';
365 for a
:= 0 to High(FResTable
) do
367 if FResTable
[a
].Length
= 0 then
369 CurrentSection
:= FResTable
[a
].ResourceName
;
373 if CurrentSection
= Section
then
375 SetLength(Result
, Length(Result
)+1);
376 Result
[High(Result
)] := FResTable
[a
].ResourceName
;
381 function TWADEditor_1
.GetSectionList(): SArray
;
387 if FResTable
= nil then Exit
;
389 if FResTable
[0].Length
<> 0 then
391 SetLength(Result
, 1);
395 for i
:= 0 to High(FResTable
) do
396 if FResTable
[i
].Length
= 0 then
398 SetLength(Result
, Length(Result
)+1);
399 Result
[High(Result
)] := FResTable
[i
].ResourceName
;
403 function TWADEditor_1
.LastErrorString(): string;
406 DFWAD_NOERROR
: Result
:= '';
407 DFWAD_ERROR_WADNOTFOUND
: Result
:= 'DFWAD file not found';
408 DFWAD_ERROR_CANTOPENWAD
: Result
:= 'Can''t open DFWAD file';
409 DFWAD_ERROR_RESOURCENOTFOUND
: Result
:= 'Resource not found';
410 DFWAD_ERROR_FILENOTWAD
: Result
:= 'File is not DFWAD';
411 DFWAD_ERROR_WADNOTLOADED
: Result
:= 'DFWAD file is not loaded';
412 DFWAD_ERROR_READRESOURCE
: Result
:= 'Read resource error';
413 DFWAD_ERROR_READWAD
: Result
:= 'Read DFWAD error';
414 else Result
:= 'Unknown DFWAD error';
418 function TWADEditor_1
.ReadFile(FileName
: string): Boolean;
421 Signature
: array[0..4] of Char;
428 if not FileExists(FileName
) then
430 FLastError
:= DFWAD_ERROR_WADNOTFOUND
;
434 FFileName
:= FileName
;
436 AssignFile(WADFile
, FFileName
);
441 FLastError
:= DFWAD_ERROR_CANTOPENWAD
;
446 BlockRead(WADFile
, Signature
, 5);
447 if Signature
<> DFWAD_SIGNATURE
then
449 FLastError
:= DFWAD_ERROR_FILENOTWAD
;
454 BlockRead(WADFile
, FVersion
, 1);
455 if FVersion
<> DFWAD_VERSION
then
457 FLastError
:= DFWAD_ERROR_WRONGVERSION
;
462 BlockRead(WADFile
, FHeader
, SizeOf(TWADHeaderRec_1
));
463 SetLength(FResTable
, FHeader
.RecordsCount
);
464 if FResTable
<> nil then
466 BlockRead(WADFile
, FResTable
[0], SizeOf(TResourceTableRec_1
)*FHeader
.RecordsCount
);
468 for a
:= 0 to High(FResTable
) do
469 if FResTable
[a
].Length
<> 0 then
470 FResTable
[a
].Address
:= FResTable
[a
].Address
-6-(LongWord(SizeOf(TWADHeaderRec_1
)+
471 SizeOf(TResourceTableRec_1
)*Length(FResTable
)));
476 FLastError
:= DFWAD_ERROR_READWAD
;
481 FWADOpened
:= DFWAD_OPENED_FILE
;
482 FLastError
:= DFWAD_NOERROR
;
486 function TWADEditor_1
.ReadMemory(Data
: Pointer; Len
: LongWord): Boolean;
488 Signature
: array[0..4] of Char;
495 CopyMemory(@Signature
[0], Data
, 5);
496 if Signature
<> DFWAD_SIGNATURE
then
498 FLastError
:= DFWAD_ERROR_FILENOTWAD
;
502 CopyMemory(@FVersion
, Pointer(LongWord(Data
)+5), 1);
503 if FVersion
<> DFWAD_VERSION
then
505 FLastError
:= DFWAD_ERROR_WRONGVERSION
;
509 CopyMemory(@FHeader
, Pointer(LongWord(Data
)+6), SizeOf(TWADHeaderRec_1
));
511 SetLength(FResTable
, FHeader
.RecordsCount
);
512 if FResTable
<> nil then
514 CopyMemory(@FResTable
[0], Pointer(LongWord(Data
)+6+SizeOf(TWADHeaderRec_1
)),
515 SizeOf(TResourceTableRec_1
)*FHeader
.RecordsCount
);
517 for a
:= 0 to High(FResTable
) do
518 if FResTable
[a
].Length
<> 0 then
519 FResTable
[a
].Address
:= FResTable
[a
].Address
-6-(LongWord(SizeOf(TWADHeaderRec_1
)+
520 SizeOf(TResourceTableRec_1
)*Length(FResTable
)));
523 GetMem(FResData
, Len
);
524 CopyMemory(FResData
, Data
, Len
);
526 FWADOpened
:= DFWAD_OPENED_MEMORY
;
527 FLastError
:= DFWAD_NOERROR
;