hedgewars/uLandObjects.pas
changeset 11383 d3b603323b2b
parent 11362 ed5a6478e710
child 11507 bd9a2f1b0080
equal deleted inserted replaced
11381:437a60995fe1 11383:d3b603323b2b
   107     bpp: LongInt;
   107     bpp: LongInt;
   108 begin
   108 begin
   109 WriteToConsole('Generating collision info... ');
   109 WriteToConsole('Generating collision info... ');
   110 
   110 
   111 if SDL_MustLock(Image) then
   111 if SDL_MustLock(Image) then
   112     SDLTry(SDL_LockSurface(Image) >= 0, true);
   112     SDLTry(SDL_LockSurface(Image) >= 0, 'SDL_LockSurface', true);
   113 
   113 
   114 bpp:= Image^.format^.BytesPerPixel;
   114 bpp:= Image^.format^.BytesPerPixel;
   115 TryDo(bpp = 4, 'Land object should be 32bit', true);
   115 TryDo(bpp = 4, 'Land object should be 32bit', true);
   116 
   116 
   117 if Width = 0 then
   117 if Width = 0 then
   158     bpp: LongInt;
   158     bpp: LongInt;
   159 begin
   159 begin
   160 WriteToConsole('Generating collision info... ');
   160 WriteToConsole('Generating collision info... ');
   161 
   161 
   162 if SDL_MustLock(Image) then
   162 if SDL_MustLock(Image) then
   163     SDLTry(SDL_LockSurface(Image) >= 0, true);
   163     SDLTry(SDL_LockSurface(Image) >= 0, 'SDL_LockSurface', true);
   164 
   164 
   165 bpp:= Image^.format^.BytesPerPixel;
   165 bpp:= Image^.format^.BytesPerPixel;
   166 TryDo(bpp = 4, 'Land object should be 32bit', true);
   166 TryDo(bpp = 4, 'Land object should be 32bit', true);
   167 
   167 
   168 p:= Image^.pixels;
   168 p:= Image^.pixels;
   206 TryDo(RectCount < MaxRects, 'AddRect: overflow', true)
   206 TryDo(RectCount < MaxRects, 'AddRect: overflow', true)
   207 end;
   207 end;
   208 
   208 
   209 procedure InitRects;
   209 procedure InitRects;
   210 begin
   210 begin
   211 RectCount:= 0;
   211     RectCount:= 0;
   212 New(Rects)
   212     New(Rects)
   213 end;
   213 end;
   214 
   214 
   215 procedure FreeRects;
   215 procedure FreeRects;
   216 begin
   216 begin
   217     Dispose(rects)
   217     Dispose(rects)
   363     else
   363     else
   364         bRes:= false;
   364         bRes:= false;
   365 CheckCanPlace:= bRes;
   365 CheckCanPlace:= bRes;
   366 end;
   366 end;
   367 
   367 
   368 function TryPut(var Obj: TThemeObject): boolean; overload;
   368 function TryPut(var Obj: TThemeObject): boolean;
   369 const MaxPointsIndex = 2047;
   369 const MaxPointsIndex = 2047;
   370 var x, y: Longword;
   370 var x, y: Longword;
   371     ar: array[0..MaxPointsIndex] of TPoint;
   371     ar: array[0..MaxPointsIndex] of TPoint;
   372     cnt, i: Longword;
   372     cnt, i: Longword;
   373     bRes: boolean;
   373     bRes: boolean;
   384         repeat
   384         repeat
   385             if CheckCanPlace(x, y, Obj) then
   385             if CheckCanPlace(x, y, Obj) then
   386                 begin
   386                 begin
   387                 ar[cnt].x:= x;
   387                 ar[cnt].x:= x;
   388                 ar[cnt].y:= y;
   388                 ar[cnt].y:= y;
   389                 inc(cnt);
   389                 if cnt >= MaxPointsIndex then // buffer is full, do not check the rest land
   390                 if cnt > MaxPointsIndex then // buffer is full, do not check the rest land
       
   391                     begin
   390                     begin
   392                     y:= LAND_HEIGHT;
   391                     y:= LAND_HEIGHT;
   393                     x:= LAND_WIDTH;
   392                     x:= LAND_WIDTH;
   394                     end
   393                     end
       
   394                     else inc(cnt);
   395                 end;
   395                 end;
   396             inc(y, 3);
   396             inc(y, 3);
   397         until y >= LAND_HEIGHT - Height;
   397         until y >= LAND_HEIGHT - Height;
   398         inc(x, getrandom(6) + 3)
   398         inc(x, getrandom(6) + 3)
   399     until x >= LAND_WIDTH - Width;
   399     until x >= LAND_WIDTH - Width;
   410     else Maxcnt:= 0
   410     else Maxcnt:= 0
   411     end;
   411     end;
   412 TryPut:= bRes;
   412 TryPut:= bRes;
   413 end;
   413 end;
   414 
   414 
   415 function TryPut(var Obj: TSprayObject; Surface: PSDL_Surface): boolean; overload;
   415 function TryPut2(var Obj: TSprayObject; Surface: PSDL_Surface): boolean;
   416 const MaxPointsIndex = 8095;
   416 const MaxPointsIndex = 8095;
   417 var x, y: Longword;
   417 var x, y: Longword;
   418     ar: array[0..MaxPointsIndex] of TPoint;
   418     ar: array[0..MaxPointsIndex] of TPoint;
   419     cnt, i: Longword;
   419     cnt, i: Longword;
   420     r: TSDL_Rect;
   420     r: TSDL_Rect;
   421     bRes: boolean;
   421     bRes: boolean;
   422 begin
   422 begin
   423 TryPut:= false;
   423 TryPut2:= false;
   424 cnt:= 0;
   424 cnt:= 0;
   425 with Obj do
   425 with Obj do
   426     begin
   426     begin
   427     if Maxcnt = 0 then
   427     if Maxcnt = 0 then
   428         exit;
   428         exit;
   437             if CheckLand(r, x, y - 8, lfBasic)
   437             if CheckLand(r, x, y - 8, lfBasic)
   438             and (not CheckIntersect(x, y, Width, Height)) then
   438             and (not CheckIntersect(x, y, Width, Height)) then
   439                 begin
   439                 begin
   440                 ar[cnt].x:= x;
   440                 ar[cnt].x:= x;
   441                 ar[cnt].y:= y;
   441                 ar[cnt].y:= y;
   442                 inc(cnt);
   442                 if cnt >= MaxPointsIndex then // buffer is full, do not check the rest land
   443                 if cnt > MaxPointsIndex then // buffer is full, do not check the rest land
       
   444                     begin
   443                     begin
   445                     y:= 5000;
   444                     y:= $FF000000;
   446                     x:= 5000;
   445                     x:= $FF000000;
   447                     end
   446                     end
       
   447                     else inc(cnt);
   448                 end;
   448                 end;
   449             inc(y, 12);
   449             inc(y, 12);
   450         until y >= LAND_HEIGHT - Height - 8;
   450         until y >= LAND_HEIGHT - Height - 8;
   451         inc(x, getrandom(12) + 12)
   451         inc(x, getrandom(12) + 12)
   452     until x >= LAND_WIDTH - Width;
   452     until x >= LAND_WIDTH - Width;
   453     bRes:= cnt <> 0;
   453     bRes:= cnt <> 0;
       
   454 AddFileLog('CHECKPOINT 004');
   454     if bRes then
   455     if bRes then
   455         begin
   456         begin
   456         i:= getrandom(cnt);
   457         i:= getrandom(cnt);
   457         r.x:= ar[i].X;
   458         r.x:= ar[i].X;
   458         r.y:= ar[i].Y;
   459         r.y:= ar[i].Y;
   462         AddRect(ar[i].x - 32, ar[i].y - 32, Width + 64, Height + 64);
   463         AddRect(ar[i].x - 32, ar[i].y - 32, Width + 64, Height + 64);
   463         dec(Maxcnt)
   464         dec(Maxcnt)
   464         end
   465         end
   465     else Maxcnt:= 0
   466     else Maxcnt:= 0
   466     end;
   467     end;
   467 TryPut:= bRes;
   468 TryPut2:= bRes;
   468 end;
   469 end;
   469 
   470 
   470 
   471 
   471 procedure CheckRect(Width, Height, x, y, w, h: LongWord);
   472 procedure CheckRect(Width, Height, x, y, w, h: LongWord);
   472 begin
   473 begin
   843 begin
   844 begin
   844     if ThemeObjects.Count = 0 then
   845     if ThemeObjects.Count = 0 then
   845         exit;
   846         exit;
   846     WriteLnToConsole('Adding theme objects...');
   847     WriteLnToConsole('Adding theme objects...');
   847 
   848 
   848     for i:=0 to ThemeObjects.Count do
   849     for i:=0 to Pred(ThemeObjects.Count) do
   849         ThemeObjects.objs[i].Maxcnt := max(1, (ThemeObjects.objs[i].Maxcnt * MaxHedgehogs) div 18); // Maxcnt is proportional to map size, but allow objects to span even if we're on a tiny map
   850         ThemeObjects.objs[i].Maxcnt := max(1, (ThemeObjects.objs[i].Maxcnt * MaxHedgehogs) div 18); // Maxcnt is proportional to map size, but allow objects to span even if we're on a tiny map
   850 
   851 
   851     repeat
   852     repeat
   852         t := getrandom(ThemeObjects.Count);
   853         t := getrandom(ThemeObjects.Count);
   853         b := false;
   854         b := false;
   854         for i:=0 to ThemeObjects.Count do
   855         for i:= 0 to Pred(ThemeObjects.Count) do
   855             begin
   856             begin
   856             ii := (i+t) mod ThemeObjects.Count;
   857             ii := (i+t) mod ThemeObjects.Count;
   857 
   858 
   858             if ThemeObjects.objs[ii].Maxcnt <> 0 then
   859             if ThemeObjects.objs[ii].Maxcnt <> 0 then
   859                 b := b or TryPut(ThemeObjects.objs[ii])
   860                 b := b or TryPut(ThemeObjects.objs[ii])
   867 begin
   868 begin
   868     if SprayObjects.Count = 0 then
   869     if SprayObjects.Count = 0 then
   869         exit;
   870         exit;
   870     WriteLnToConsole('Adding spray objects...');
   871     WriteLnToConsole('Adding spray objects...');
   871 
   872 
   872     for i:=0 to SprayObjects.Count do
   873     for i:= 0 to Pred(SprayObjects.Count) do
   873         SprayObjects.objs[i].Maxcnt := max(1, (SprayObjects.objs[i].Maxcnt * MaxHedgehogs) div 18); // Maxcnt is proportional to map size, but allow objects to span even if we're on a tiny map
   874         SprayObjects.objs[i].Maxcnt := max(1, (SprayObjects.objs[i].Maxcnt * MaxHedgehogs) div 18); // Maxcnt is proportional to map size, but allow objects to span even if we're on a tiny map
   874 
   875 
   875     repeat
   876     repeat
   876         t := getrandom(SprayObjects.Count);
   877         t := getrandom(SprayObjects.Count);
   877         b := false;
   878         b := false;
   878         for i:=0 to SprayObjects.Count do
   879         for i:= 0 to Pred(SprayObjects.Count) do
   879             begin
   880             begin
   880             ii := (i+t) mod SprayObjects.Count;
   881             ii := (i+t) mod SprayObjects.Count;
   881 
   882 
   882             if SprayObjects.objs[ii].Maxcnt <> 0 then
   883             if SprayObjects.objs[ii].Maxcnt <> 0 then
   883                 b := b or TryPut(SprayObjects.objs[ii], Surface)
   884                 b := b or TryPut2(SprayObjects.objs[ii], Surface)
   884             end;
   885             end;
   885     until not b;
   886     until not b;
   886 end;
   887 end;
   887 
   888 
   888 procedure AddObjects();
   889 procedure AddObjects();
   913 end;
   914 end;
   914 
   915 
   915 procedure AddOnLandObjects(Surface: PSDL_Surface);
   916 procedure AddOnLandObjects(Surface: PSDL_Surface);
   916 begin
   917 begin
   917 InitRects;
   918 InitRects;
   918 //AddSprayObjects(Surface, SprayObjects, 12);
       
   919 AddSprayObjects(Surface, SprayObjects);
   919 AddSprayObjects(Surface, SprayObjects);
   920 FreeRects
   920 FreeRects
   921 end;
   921 end;
   922 
   922 
   923 procedure LoadThemeConfig;
   923 procedure LoadThemeConfig;