hedgewars/uAIMisc.pas
changeset 80 3c3dc6a148ca
parent 79 29b477319854
child 82 2f4f3236cccc
equal deleted inserted replaced
79:29b477319854 80:3c3dc6a148ca
    32  *)
    32  *)
    33 
    33 
    34 unit uAIMisc;
    34 unit uAIMisc;
    35 interface
    35 interface
    36 uses SDLh, uConsts, uGears;
    36 uses SDLh, uConsts, uGears;
       
    37 {$INCLUDE options.inc}
    37 
    38 
    38 type TTarget = record
    39 type TTarget = record
    39                Point: TPoint;
    40                Point: TPoint;
    40                Score: integer;
    41                Score: integer;
    41                end;
    42                end;
    42      TTargets = record
    43      TTargets = record
    43                 Count: Longword;
    44                 Count: Longword;
    44                 ar: array[0..cMaxHHIndex*5] of TTarget;
    45                 ar: array[0..cMaxHHIndex*5] of TTarget;
    45                 end;
    46                 end;
       
    47      TJumpType = (jmpNone, jmpHJump, jmpLJump);
    46      TGoInfo = record
    48      TGoInfo = record
    47                Ticks: Longword;
    49                Ticks: Longword;
    48                FallTicks: Longword;
    50                FallPix: Longword;
       
    51                JumpType: TJumpType;
    49                end;
    52                end;
    50 
    53 
    51 procedure FillTargets;
    54 procedure FillTargets;
    52 procedure FillBonuses(isAfterAttack: boolean);
    55 procedure FillBonuses(isAfterAttack: boolean);
    53 procedure AwareOfExplosion(x, y, r: integer);
    56 procedure AwareOfExplosion(x, y, r: integer);
    54 function RatePlace(Gear: PGear): integer;
    57 function RatePlace(Gear: PGear): integer;
    55 function DxDy2AttackAngle(const _dY, _dX: Extended): integer;
    58 function DxDy2AttackAngle(const _dY, _dX: Extended): integer;
    56 function TestColl(x, y, r: integer): boolean;
    59 function TestColl(x, y, r: integer): boolean;
    57 function RateExplosion(Me: PGear; x, y, r: integer): integer;
    60 function RateExplosion(Me: PGear; x, y, r: integer): integer;
    58 function RateShove(Me: PGear; x, y, r, power: integer): integer;
    61 function RateShove(Me: PGear; x, y, r, power: integer): integer;
    59 function HHGo(Gear: PGear; out GoInfo: TGoInfo): boolean;
    62 function HHGo(Gear, AltGear: PGear; out GoInfo: TGoInfo): boolean;
    60 
    63 
    61 var ThinkingHH: PGear;
    64 var ThinkingHH: PGear;
    62     Targets: TTargets;
    65     Targets: TTargets;
    63 
    66 
    64 implementation
    67 implementation
   236             end;
   239             end;
   237          end;
   240          end;
   238 Result:= Result * 1024
   241 Result:= Result * 1024
   239 end;
   242 end;
   240 
   243 
   241 function HHGo(Gear: PGear; out GoInfo: TGoInfo): boolean;
   244 function HHJump(Gear: PGear; JumpType: TJumpType; out GoInfo: TGoInfo): boolean;
   242 var pX, pY: integer;
   245 var bX, bY: integer;
   243 begin
   246 begin
   244 Result:= false;
   247 Result:= false;
   245 GoInfo.Ticks:= 0;
   248 GoInfo.Ticks:= 0;
   246 GoInfo.FallTicks:= 0;
   249 GoInfo.FallPix:= 0;
       
   250 GoInfo.JumpType:= jmpNone;
       
   251 bX:= round(Gear.X);
       
   252 bY:= round(Gear.Y);
       
   253 case JumpType of
       
   254      jmpNone: exit;
       
   255     jmpHJump: if not TestCollisionYwithGear(Gear, -1) then
       
   256                  begin
       
   257                  Gear.dY:= -0.20;
       
   258                  Gear.dX:= 0.0000001 * Sign(Gear.dX);
       
   259                  Gear.X:= Gear.X - Sign(Gear.dX)*0.00008; // shift compensation
       
   260                  Gear.State:= Gear.State or gstFalling or gstHHJumping;
       
   261                  end else exit;
       
   262     jmpLJump: begin
       
   263               if not TestCollisionYwithGear(Gear, -1) then
       
   264                  if not TestCollisionXwithXYShift(Gear, 0, -2, Sign(Gear.dX)) then Gear.Y:= Gear.Y - 2 else
       
   265                  if not TestCollisionXwithXYShift(Gear, 0, -1, Sign(Gear.dX)) then Gear.Y:= Gear.Y - 1;
       
   266               if not (TestCollisionXwithGear(Gear, Sign(Gear.dX))
       
   267                  or   TestCollisionYwithGear(Gear, -1)) then
       
   268                  begin
       
   269                  Gear.dY:= -0.15;
       
   270                  Gear.dX:= Sign(Gear.dX) * 0.15;
       
   271                  Gear.State:= Gear.State or gstFalling or gstHHJumping
       
   272                  end
       
   273               end
       
   274     end;
       
   275     
       
   276 repeat
       
   277 if Gear.Y + cHHRadius >= cWaterLine then exit;
       
   278 if (Gear.State and gstFalling) <> 0 then
       
   279    begin
       
   280    if (GoInfo.Ticks = 350) then
       
   281       if (abs(Gear.dX) < 0.0000002) and (Gear.dY < -0.02) then
       
   282          begin
       
   283          Gear.dY:= -0.25;
       
   284          Gear.dX:= Sign(Gear.dX) * 0.02
       
   285          end;
       
   286    if TestCollisionXwithGear(Gear, Sign(Gear.dX)) then Gear.dX:= 0.0000001 * Sign(Gear.dX);
       
   287    Gear.X:= Gear.X + Gear.dX;
       
   288    inc(GoInfo.Ticks);
       
   289    Gear.dY:= Gear.dY + cGravity;
       
   290    if Gear.dY > 0.40 then exit;
       
   291    if (Gear.dY < 0)and TestCollisionYwithGear(Gear, -1) then Gear.dY:= 0; 
       
   292    Gear.Y:= Gear.Y + Gear.dY;
       
   293    if (Gear.dY >= 0)and TestCollisionYwithGear(Gear, 1) then
       
   294       begin
       
   295       Gear.State:= Gear.State and not (gstFalling or gstHHJumping);
       
   296       Gear.dY:= 0;
       
   297       case JumpType of
       
   298            jmpHJump: if (bY - Gear.Y > 5) then
       
   299                         begin
       
   300                         Result:= true;
       
   301                         GoInfo.JumpType:= jmpHJump;
       
   302                         inc(GoInfo.Ticks, 300 + 300) // 300 before jump, 300 after
       
   303                         end;
       
   304            jmpLJump: if abs(bX - Gear.X) > 30 then
       
   305                         begin
       
   306                         Result:= true;
       
   307                         GoInfo.JumpType:= jmpLJump;
       
   308                         inc(GoInfo.Ticks, 300 + 300) // 300 before jump, 300 after
       
   309                         end;
       
   310            end;
       
   311       exit
       
   312       end;
       
   313    end;
       
   314 until false;
       
   315 end;
       
   316 
       
   317 function HHGo(Gear, AltGear: PGear; out GoInfo: TGoInfo): boolean;
       
   318 var pX, pY: integer;
       
   319 begin
       
   320 Result:= false;
       
   321 AltGear^:= Gear^;
       
   322 
       
   323 GoInfo.Ticks:= 0;
       
   324 GoInfo.FallPix:= 0;
       
   325 GoInfo.JumpType:= jmpNone;
   247 repeat
   326 repeat
   248 pX:= round(Gear.X);
   327 pX:= round(Gear.X);
   249 pY:= round(Gear.Y);
   328 pY:= round(Gear.Y);
   250 if pY + cHHRadius >= cWaterLine then exit;
   329 if pY + cHHRadius >= cWaterLine then exit;
   251 if (Gear.State and gstFalling) <> 0 then
   330 if (Gear.State and gstFalling) <> 0 then
   252    begin
   331    begin
   253    inc(GoInfo.Ticks);
   332    inc(GoInfo.Ticks);
   254    Gear.dY:= Gear.dY + cGravity;
   333    Gear.dY:= Gear.dY + cGravity;
   255    if Gear.dY > 0.40 then
   334    if Gear.dY > 0.40 then
   256       begin
   335       begin
   257       Goinfo.FallTicks:= 0;
   336       Goinfo.FallPix:= 0;
       
   337       HHJump(AltGear, jmpLJump, GoInfo);
   258       exit
   338       exit
   259       end;
   339       end;
   260    Gear.Y:= Gear.Y + Gear.dY;
   340    Gear.Y:= Gear.Y + Gear.dY;
   261    if round(Gear.Y) > pY then inc(GoInfo.FallTicks);
   341    if round(Gear.Y) > pY then inc(GoInfo.FallPix);
   262    if TestCollisionYwithGear(Gear, 1) then
   342    if TestCollisionYwithGear(Gear, 1) then
   263       begin
   343       begin
   264       inc(GoInfo.Ticks, 300);
   344       inc(GoInfo.Ticks, 300);
   265       Gear.State:= Gear.State and not (gstFalling or gstHHJumping);
   345       Gear.State:= Gear.State and not (gstFalling or gstHHJumping);
   266       Gear.dY:= 0;
   346       Gear.dY:= 0;
   267       Result:= true;
   347       Result:= true;
       
   348       HHJump(AltGear, jmpLJump, GoInfo);
   268       exit
   349       exit
   269       end;
   350       end;
   270    continue
   351    continue
   271    end;
   352    end;
   272    {if ((Gear.Message and gm_LJump )<>0) then
       
   273       begin
       
   274       Gear.Message:= 0;
       
   275       if not HHTestCollisionYwithGear(Gear, -1) then
       
   276          if not TestCollisionXwithXYShift(Gear, 0, -2, Sign(Gear.dX)) then Gear.Y:= Gear.Y - 2 else
       
   277          if not TestCollisionXwithXYShift(Gear, 0, -1, Sign(Gear.dX)) then Gear.Y:= Gear.Y - 1;
       
   278       if not (TestCollisionXwithGear(Gear, Sign(Gear.dX))
       
   279          or   HHTestCollisionYwithGear(Gear, -1)) then
       
   280          begin
       
   281          Gear.dY:= -0.15;
       
   282          Gear.dX:= Sign(Gear.dX) * 0.15;
       
   283          Gear.State:= Gear.State or gstFalling or gstHHJumping;
       
   284          exit
       
   285          end;
       
   286       end;}
       
   287    if (Gear.Message and gm_Left  )<>0 then Gear.dX:= -1.0 else
   353    if (Gear.Message and gm_Left  )<>0 then Gear.dX:= -1.0 else
   288    if (Gear.Message and gm_Right )<>0 then Gear.dX:=  1.0 else exit;
   354    if (Gear.Message and gm_Right )<>0 then Gear.dX:=  1.0 else exit;
   289    if TestCollisionXwithGear(Gear, Sign(Gear.dX)) then
   355    if TestCollisionXwithGear(Gear, Sign(Gear.dX)) then
   290       begin
   356       begin
   291       if not (TestCollisionXwithXYShift(Gear, 0, -6, Sign(Gear.dX))
   357       if not (TestCollisionXwithXYShift(Gear, 0, -6, Sign(Gear.dX))
   342    begin
   408    begin
   343    Result:= true;
   409    Result:= true;
   344    exit
   410    exit
   345    end
   411    end
   346 until (pX = round(Gear.X)) and (pY = round(Gear.Y)) and ((Gear.State and gstFalling) = 0);
   412 until (pX = round(Gear.X)) and (pY = round(Gear.Y)) and ((Gear.State and gstFalling) = 0);
       
   413 HHJump(AltGear, jmpHJump, GoInfo)
   347 end;
   414 end;
   348 
   415 
   349 end.
   416 end.