DEADSOFTWARE

no more path splitting in wad reading, it's useless
[d2df-sdl.git] / src / game / g_map.pas
index 584a88f2b637679b28d719d0def9c9d38cfe6e42..6c156caf5c973912a371ba6e4c0fc9397dce1467 100644 (file)
@@ -1,10 +1,11 @@
+{$MODE DELPHI}
 unit g_map;
 
 interface
 
 uses
   e_graphics, g_basic, MAPSTRUCT, g_textures, Classes,
-  g_phys, WADEDITOR, BinEditor, g_panel, md5;
+  g_phys, wadreader, BinEditor, g_panel, md5;
 
 type
   TMapInfo = record
@@ -346,9 +347,10 @@ begin
   Result := len;
 end;
 
-procedure CreateNullTexture(RecName: String);
+function CreateNullTexture(RecName: String): Integer;
 begin
   SetLength(Textures, Length(Textures)+1);
+  result := High(Textures);
 
   with Textures[High(Textures)] do
   begin
@@ -360,22 +362,20 @@ begin
   end;
 end;
 
-function CreateTexture(RecName: String; Map: string; log: Boolean): Boolean;
+function CreateTexture(RecName: String; Map: string; log: Boolean): Integer;
 var
-  WAD: TWADEditor_1;
+  WAD: TWADFile;
   TextureData: Pointer;
   WADName: String;
-  SectionName: String;
-  TextureName: String;
   a, ResLength: Integer;
 begin
-  Result := False;
+  Result := -1;
 
   if Textures <> nil then
     for a := 0 to High(Textures) do
       if Textures[a].TextureName = RecName then
       begin // Òåêñòóðà ñ òàêèì èìåíåì óæå åñòü
-        Result := True;
+        Result := a;
         Exit;
       end;
 
@@ -402,14 +402,14 @@ begin
       Anim := False;
     end;
 
-    Result := True;
+    result := High(Textures);
     Exit;
   end;
 
 // Çàãðóæàåì ðåñóðñ òåêñòóðû â ïàìÿòü èç WAD'à:
-  g_ProcessResourceStr(RecName, WADName, SectionName, TextureName);
+  WADName := g_ExtractWadName(RecName);
 
-  WAD := TWADEditor_1.Create();
+  WAD := TWADFile.Create();
 
   if WADName <> '' then
     WADName := GameDir+'/wads/'+WADName
@@ -418,10 +418,10 @@ begin
 
   WAD.ReadFile(WADName);
 
-  if WAD.GetResource(SectionName, TextureName, TextureData, ResLength) then
+  if WAD.GetResource(g_ExtractFilePathName(RecName), TextureData, ResLength) then
     begin
       SetLength(Textures, Length(Textures)+1);
-      if not e_CreateTextureMem(TextureData, Textures[High(Textures)].TextureID) then
+      if not e_CreateTextureMem(TextureData, ResLength, Textures[High(Textures)].TextureID) then
         Exit;
       e_GetTextureSize(Textures[High(Textures)].TextureID,
                        @Textures[High(Textures)].Width,
@@ -430,7 +430,7 @@ begin
       Textures[High(Textures)].TextureName := RecName;
       Textures[High(Textures)].Anim := False;
 
-      Result := True;
+      result := High(Textures);
     end
   else // Íåò òàêîãî ðåóñðñà â WAD'å
     if log then
@@ -442,27 +442,25 @@ begin
   WAD.Free();
 end;
 
-function CreateAnimTexture(RecName: String; Map: string; log: Boolean): Boolean;
+function CreateAnimTexture(RecName: String; Map: string; log: Boolean): Integer;
 var
-  WAD: TWADEditor_1;
+  WAD: TWADFile;
   TextureWAD: Pointer;
   TextData: Pointer;
   TextureData: Pointer;
   cfg: TConfig;
   WADName: String;
-  SectionName: String;
-  TextureName: String;
   ResLength: Integer;
   TextureResource: String;
   _width, _height, _framecount, _speed: Integer;
   _backanimation: Boolean;
 begin
-  Result := False;
+  Result := -1;
 
 // ×èòàåì WAD-ðåñóðñ àíèì.òåêñòóðû èç WAD'à â ïàìÿòü:
-  g_ProcessResourceStr(RecName, WADName, SectionName, TextureName);
+  WADName := g_ExtractWadName(RecName);
 
-  WAD := TWADEditor_1.Create();
+  WAD := TWADFile.Create();
 
   if WADName <> '' then
     WADName := GameDir+'/wads/'+WADName
@@ -471,7 +469,7 @@ begin
 
   WAD.ReadFile(WADName);
 
-  if not WAD.GetResource(SectionName, TextureName, TextureWAD, ResLength) then
+  if not WAD.GetResource(g_ExtractFilePathName(RecName), TextureWAD, ResLength) then
   begin
     if log then
     begin
@@ -492,7 +490,7 @@ begin
   end;
 
 // ×èòàåì INI-ðåñóðñ àíèì. òåêñòóðû è çàïîìèíàåì åãî óñòàíîâêè:
-  if not WAD.GetResource('TEXT', 'ANIM', TextData, ResLength) then
+  if not WAD.GetResource('TEXT/ANIM', TextData, ResLength) then
   begin
     FreeMem(TextureWAD);
     WAD.Free();
@@ -521,7 +519,7 @@ begin
   cfg.Free();
 
 // ×èòàåì ðåñóðñ òåêñòóð (êàäðîâ) àíèì. òåêñòóðû â ïàìÿòü:
-  if not WAD.GetResource('TEXTURES', TextureResource, TextureData, ResLength) then
+  if not WAD.GetResource('TEXTURES/'+TextureResource, TextureData, ResLength) then
   begin
     FreeMem(TextureWAD);
     FreeMem(TextData);
@@ -535,7 +533,7 @@ begin
   with Textures[High(Textures)] do
   begin
   // Ñîçäàåì êàäðû àíèì. òåêñòóðû èç ïàìÿòè:
-    if g_Frames_CreateMemory(@FramesID, '', TextureData,
+    if g_Frames_CreateMemory(@FramesID, '', TextureData, ResLength,
          _width, _height, _framecount, _backanimation) then
       begin
         TextureName := RecName;
@@ -545,7 +543,7 @@ begin
         FramesCount := _framecount;
         Speed := _speed;
 
-        Result := True;
+        result := High(Textures);
       end
     else
       if log then
@@ -754,10 +752,11 @@ const
   DefaultMusRes = 'Standart.wad:STDMUS\MUS1';
   DefaultSkyRes = 'Standart.wad:STDSKY\SKY0';
 var
-  WAD: TWADEditor_1;
+  WAD: TWADFile;
   MapReader: TMapReader_1;
   Header: TMapHeaderRec_1;
   _textures: TTexturesRec1Array;
+  _texnummap: array of Integer; // `_textures` -> `Textures`
   panels: TPanelsRec1Array;
   items: TItemsRec1Array;
   monsters: TMonsterRec1Array;
@@ -773,12 +772,11 @@ var
                            DoorPanel: Integer;
                            ShotPanel: Integer;
                           end;
-  FileName, SectionName, ResName,
-  FileName2, s, TexName: String;
+  FileName, mapResName, s, TexName: String;
   Data: Pointer;
   Len: Integer;
   ok, isAnim, trigRef: Boolean;
-  CurTex: Integer;
+  CurTex, ntn: Integer;
 begin
   Result := False;
   gMapInfo.Map := Res;
@@ -788,27 +786,29 @@ begin
   sfsGCDisable(); // temporary disable removing of temporary volumes
   try
   // Çàãðóçêà WAD:
-    g_ProcessResourceStr(Res, FileName, SectionName, ResName);
-    e_WriteLog('Loading map WAD: ' + FileName, MSG_NOTIFY);
+    FileName := g_ExtractWadName(Res);
+    e_WriteLog('Loading map WAD: '+FileName, MSG_NOTIFY);
     g_Game_SetLoadingText(_lc[I_LOAD_WAD_FILE], 0, False);
 
-    WAD := TWADEditor_1.Create();
+    WAD := TWADFile.Create();
     if not WAD.ReadFile(FileName) then
     begin
       g_FatalError(Format(_lc[I_GAME_ERROR_MAP_WAD], [FileName]));
       WAD.Free();
       Exit;
     end;
-    if not WAD.GetResource('', ResName, Data, Len) then
+    //k8: why loader ignores path here?
+    mapResName := g_ExtractFileName(Res);
+    if not WAD.GetResource(mapResName, Data, Len) then
     begin
-      g_FatalError(Format(_lc[I_GAME_ERROR_MAP_RES], [ResName]));
+      g_FatalError(Format(_lc[I_GAME_ERROR_MAP_RES], [mapResName]));
       WAD.Free();
       Exit;
     end;
     WAD.Free();
 
   // Çàãðóçêà êàðòû:
-    e_WriteLog('Loading map: ' + ResName, MSG_NOTIFY);
+    e_WriteLog('Loading map: '+mapResName, MSG_NOTIFY);
     g_Game_SetLoadingText(_lc[I_LOAD_MAP], 0, False);
     MapReader := TMapReader_1.Create();
 
@@ -825,12 +825,14 @@ begin
   // Çàãðóçêà òåêñòóð:
     g_Game_SetLoadingText(_lc[I_LOAD_TEXTURES], 0, False);
     _textures := MapReader.GetTextures();
+    _texnummap := nil;
 
   // Äîáàâëåíèå òåêñòóð â Textures[]:
     if _textures <> nil then
     begin
       e_WriteLog('  Loading textures:', MSG_NOTIFY);
       g_Game_SetLoadingText(_lc[I_LOAD_TEXTURES], High(_textures), False);
+      SetLength(_texnummap, length(_textures));
 
       for a := 0 to High(_textures) do
       begin
@@ -842,23 +844,27 @@ begin
             SetLength(s, b-1);
             Break;
           end;
-        e_WriteLog('    Loading texture: ' + s, MSG_NOTIFY);
+        e_WriteLog(Format('    Loading texture #%d: %s', [a, s]), MSG_NOTIFY);
+        //if g_Map_IsSpecialTexture(s) then e_WriteLog('      SPECIAL!', MSG_NOTIFY);
       // Àíèìèðîâàííàÿ òåêñòóðà:
         if ByteBool(_textures[a].Anim) then
           begin
-            if not CreateAnimTexture(_textures[a].Resource, FileName, True) then
+            ntn := CreateAnimTexture(_textures[a].Resource, FileName, True);
+            if ntn < 0 then
             begin
               g_SimpleError(Format(_lc[I_GAME_ERROR_TEXTURE_ANIM], [s]));
-              CreateNullTexture(_textures[a].Resource);
+              ntn := CreateNullTexture(_textures[a].Resource);
             end;
           end
         else // Îáû÷íàÿ òåêñòóðà:
-          if not CreateTexture(_textures[a].Resource, FileName, True) then
+          ntn := CreateTexture(_textures[a].Resource, FileName, True);
+          if ntn < 0 then
           begin
             g_SimpleError(Format(_lc[I_GAME_ERROR_TEXTURE_SIMPLE], [s]));
-            CreateNullTexture(_textures[a].Resource);
+            ntn := CreateNullTexture(_textures[a].Resource);
           end;
 
+        _texnummap[a] := ntn; // fix texture number
         g_Game_StepLoading();
       end;
     end;
@@ -874,6 +880,18 @@ begin
     g_Game_SetLoadingText(_lc[I_LOAD_PANELS], 0, False);
     panels := MapReader.GetPanels();
 
+    // check texture numbers for panels
+    for a := 0 to High(panels) do
+    begin
+      if panels[a].TextureNum > High(_textures) then
+      begin
+        e_WriteLog('error loading map: invalid texture index for panel', MSG_FATALERROR);
+        result := false;
+        exit;
+      end;
+      panels[a].TextureNum := _texnummap[panels[a].TextureNum];
+    end;
+
   // Ñîçäàíèå òàáëèöû òðèããåðîâ (ñîîòâåòñòâèå ïàíåëåé òðèããåðàì):
     if triggers <> nil then
     begin
@@ -981,21 +999,21 @@ begin
                   if ByteBool(texture.Anim) then
                     begin // Íà÷àëüíàÿ - àíèìèðîâàííàÿ, èùåì àíèìèðîâàííóþ
                       isAnim := True;
-                      ok := CreateAnimTexture(TexName, FileName, False);
+                      ok := CreateAnimTexture(TexName, FileName, False) >= 0;
                       if not ok then
                       begin // Íåò àíèìèðîâàííîé, èùåì îáû÷íóþ
                         isAnim := False;
-                        ok := CreateTexture(TexName, FileName, False);
+                        ok := CreateTexture(TexName, FileName, False) >= 0;
                       end;
                     end
                   else
                     begin // Íà÷àëüíàÿ - îáû÷íàÿ, èùåì îáû÷íóþ
                       isAnim := False;
-                      ok := CreateTexture(TexName, FileName, False);
+                      ok := CreateTexture(TexName, FileName, False) >= 0;
                       if not ok then
                       begin // Íåò îáû÷íîé, èùåì àíèìèðîâàííóþ
                         isAnim := True;
-                        ok := CreateAnimTexture(TexName, FileName, False);
+                        ok := CreateAnimTexture(TexName, FileName, False) >= 0;
                       end;
                     end;
 
@@ -1039,6 +1057,8 @@ begin
           CurTex := 0;
         end;
 
+        //e_WriteLog(Format('panel #%d: TextureNum=%d; ht=%d; ht1=%d; atl=%d', [a, panels[a].TextureNum, High(_textures), High(Textures), High(AddTextures)]), MSG_NOTIFY);
+
       // Ñîçäàåì ïàíåëü è çàïîìèíàåì åå íîìåð:
         PanelID := CreatePanel(panels[a], AddTextures, CurTex, trigRef);
 
@@ -1150,17 +1170,16 @@ begin
     begin
       e_WriteLog('  Loading sky: ' + gMapInfo.SkyName, MSG_NOTIFY);
       g_Game_SetLoadingText(_lc[I_LOAD_SKY], 0, False);
-      g_ProcessResourceStr(gMapInfo.SkyName, FileName, SectionName, ResName);
+      FileName := g_ExtractWadName(gMapInfo.SkyName);
 
       if FileName <> '' then
         FileName := GameDir+'/wads/'+FileName
       else
         begin
-          g_ProcessResourceStr(Res, @FileName2, nil, nil);
-          FileName := FileName2;
+          FileName := g_ExtractWadName(Res);
         end;
 
-      s := FileName+':'+SectionName+'/'+ResName;
+      s := FileName+':'+g_ExtractFilePathName(gMapInfo.SkyName);
       if g_Texture_CreateWAD(BackID, s) then
         begin
           g_Game_SetupScreenSize();
@@ -1175,17 +1194,16 @@ begin
     begin
       e_WriteLog('  Loading music: ' + gMapInfo.MusicName, MSG_NOTIFY);
       g_Game_SetLoadingText(_lc[I_LOAD_MUSIC], 0, False);
-      g_ProcessResourceStr(gMapInfo.MusicName, FileName, SectionName, ResName);
+      FileName := g_ExtractWadName(gMapInfo.MusicName);
 
       if FileName <> '' then
         FileName := GameDir+'/wads/'+FileName
       else
         begin
-          g_ProcessResourceStr(Res, @FileName2, nil, nil);
-          FileName := FileName2;
+          FileName := g_ExtractWadName(Res);
         end;
 
-      s := FileName+':'+SectionName+'/'+ResName;
+      s := FileName+':'+g_ExtractFilePathName(gMapInfo.MusicName);
       if g_Sound_CreateWADEx(gMapInfo.MusicName, s, True) then
         ok := True
       else
@@ -1231,24 +1249,25 @@ end;
 
 function g_Map_GetMapInfo(Res: String): TMapInfo;
 var
-  WAD: TWADEditor_1;
+  WAD: TWADFile;
   MapReader: TMapReader_1;
   Header: TMapHeaderRec_1;
-  FileName, SectionName, ResName: String;
+  FileName: String;
   Data: Pointer;
   Len: Integer;
 begin
   FillChar(Result, SizeOf(Result), 0);
-  g_ProcessResourceStr(Res, FileName, SectionName, ResName);
+  FileName := g_ExtractWadName(Res);
 
-  WAD := TWADEditor_1.Create();
+  WAD := TWADFile.Create();
   if not WAD.ReadFile(FileName) then
   begin
     WAD.Free();
     Exit;
   end;
 
-  if not WAD.GetResource('', ResName, Data, Len) then
+  //k8: it ignores path again
+  if not WAD.GetResource(g_ExtractFileName(Res), Data, Len) then
   begin
     WAD.Free();
     Exit;
@@ -1283,7 +1302,7 @@ end;
 
 function g_Map_GetMapsList(WADName: string): SArray;
 var
-  WAD: TWADEditor_1;
+  WAD: TWADFile;
   a: Integer;
   ResList: SArray;
   Data: Pointer;
@@ -1292,19 +1311,19 @@ var
 begin
   Result := nil;
 
-  WAD := TWADEditor_1.Create();
+  WAD := TWADFile.Create();
   if not WAD.ReadFile(WADName) then
   begin
     WAD.Free();
     Exit;
   end;
 
-  ResList := WAD.GetResourcesList('');
+  ResList := WAD.GetRootResources();
 
   if ResList <> nil then
     for a := 0 to High(ResList) do
     begin
-      if not WAD.GetResource('', ResList[a], Data, Len) then Continue;
+      if not WAD.GetResource(ResList[a], Data, Len) then Continue;
       CopyMemory(@Sign[0], Data, 3);
       FreeMem(Data);
 
@@ -1322,29 +1341,28 @@ end;
 
 function g_Map_Exist(Res: string): Boolean;
 var
-  WAD: TWADEditor_1;
-  FileName, SectionName, ResName: string;
+  WAD: TWADFile;
+  FileName, mnn: string;
   ResList: SArray;
   a: Integer;
 begin
   Result := False;
 
-  g_ProcessResourceStr(Res, FileName, SectionName, ResName);
-
-  FileName := addWadExtension(FileName);
+  FileName := addWadExtension(g_ExtractWadName(Res));
 
-  WAD := TWADEditor_1.Create;
+  WAD := TWADFile.Create;
   if not WAD.ReadFile(FileName) then
   begin
     WAD.Free();
     Exit;
   end;
 
-  ResList := WAD.GetResourcesList('');
+  ResList := WAD.GetRootResources();
   WAD.Free();
 
+  mnn := g_ExtractFileName(Res);
   if ResList <> nil then
-    for a := 0 to High(ResList) do if ResList[a] = ResName then
+    for a := 0 to High(ResList) do if StrEquCI1251(ResList[a], mnn) then
     begin
       Result := True;
       Exit;