214 // Wrapper to test various approaches. If it works reasonably, will just replace. |
214 // Wrapper to test various approaches. If it works reasonably, will just replace. |
215 // Right now, converting to hwFloat is a tad inefficient since the x/y were hwFloat to begin with... |
215 // Right now, converting to hwFloat is a tad inefficient since the x/y were hwFloat to begin with... |
216 function TestCollExcludingMe(Me: PGear; x, y, r: LongInt): boolean; inline; |
216 function TestCollExcludingMe(Me: PGear; x, y, r: LongInt): boolean; inline; |
217 var MeX, MeY: LongInt; |
217 var MeX, MeY: LongInt; |
218 begin |
218 begin |
219 TestCollExcludingMe:= false; |
|
220 if ((x and LAND_WIDTH_MASK) = 0) and ((y and LAND_HEIGHT_MASK) = 0) then |
219 if ((x and LAND_WIDTH_MASK) = 0) and ((y and LAND_HEIGHT_MASK) = 0) then |
221 begin |
220 begin |
222 MeX:= hwRound(Me^.X); |
221 MeX:= hwRound(Me^.X); |
223 MeY:= hwRound(Me^.Y); |
222 MeY:= hwRound(Me^.Y); |
224 // We are still inside the hog. Skip radius test |
223 // We are still inside the hog. Skip radius test |
225 if ((((x-MeX)*(x-MeX)) + ((y-MeY)*(y-MeY))) < 256) and ((Land[y, x] and $FF00) = 0) then |
224 if ((((x-MeX)*(x-MeX)) + ((y-MeY)*(y-MeY))) < 256) and ((Land[y, x] and $FF00) = 0) then |
226 exit; |
225 exit(false); |
227 end; |
226 end; |
228 TestCollExcludingMe:= TestColl(x, y, r) |
227 TestCollExcludingMe:= TestColl(x, y, r) |
229 end; |
228 end; |
230 |
229 |
231 function TestColl(x, y, r: LongInt): boolean; inline; |
230 function TestColl(x, y, r: LongInt): boolean; inline; |
232 var b: boolean; |
231 var b: boolean; |
233 begin |
232 begin |
234 TestColl:= true; |
|
235 |
|
236 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x-r] <> 0); |
233 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x-r] <> 0); |
237 if b then |
234 if b then |
238 exit; |
235 exit(true); |
239 |
236 |
240 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x-r] <> 0); |
237 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x-r] <> 0); |
241 if b then |
238 if b then |
242 exit; |
239 exit(true); |
243 |
240 |
244 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x+r] <> 0); |
241 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x+r] <> 0); |
245 if b then |
242 if b then |
246 exit; |
243 exit(true); |
247 |
244 |
248 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x+r] <> 0); |
245 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x+r] <> 0); |
249 if b then |
246 if b then |
250 exit; |
247 exit(true); |
251 |
248 |
252 TestColl:= false; |
249 TestColl:= false; |
253 end; |
250 end; |
254 |
251 |
255 function TestCollWithLand(x, y, r: LongInt): boolean; inline; |
252 function TestCollWithLand(x, y, r: LongInt): boolean; inline; |
256 var b: boolean; |
253 var b: boolean; |
257 begin |
254 begin |
258 TestCollWithLand:= true; |
|
259 |
|
260 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x-r] > 255); |
255 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x-r] > 255); |
261 if b then |
256 if b then |
262 exit; |
257 exit(true); |
263 |
258 |
264 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x-r] > 255); |
259 b:= (((x-r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x-r] > 255); |
265 if b then |
260 if b then |
266 exit; |
261 exit(true); |
267 |
262 |
268 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x+r] > 255); |
263 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y-r) and LAND_HEIGHT_MASK) = 0) and (Land[y-r, x+r] > 255); |
269 if b then |
264 if b then |
270 exit; |
265 exit(true); |
271 |
266 |
272 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x+r] > 255); |
267 b:= (((x+r) and LAND_WIDTH_MASK) = 0) and (((y+r) and LAND_HEIGHT_MASK) = 0) and (Land[y+r, x+r] > 255); |
273 if b then |
268 if b then |
274 exit; |
269 exit(true); |
275 |
270 |
276 TestCollWithLand:= false; |
271 TestCollWithLand:= false; |
277 end; |
272 end; |
278 |
273 |
279 function TraceFall(eX, eY: LongInt; x, y, dX, dY: Real; r: LongWord): LongInt; |
274 function TraceFall(eX, eY: LongInt; x, y, dX, dY: Real; r: LongWord): LongInt; |
533 GoInfo.Ticks:= 0; |
513 GoInfo.Ticks:= 0; |
534 GoInfo.JumpType:= jmpNone; |
514 GoInfo.JumpType:= jmpNone; |
535 bX:= hwRound(Gear^.X); |
515 bX:= hwRound(Gear^.X); |
536 bY:= hwRound(Gear^.Y); |
516 bY:= hwRound(Gear^.Y); |
537 case JumpType of |
517 case JumpType of |
538 jmpNone: exit; |
518 jmpNone: exit(false); |
539 |
519 |
540 jmpHJump: |
520 jmpHJump: |
541 if TestCollisionYwithGear(Gear, -1) = 0 then |
521 if TestCollisionYwithGear(Gear, -1) = 0 then |
542 begin |
522 begin |
543 Gear^.dY:= -_0_2; |
523 Gear^.dY:= -_0_2; |
544 SetLittle(Gear^.dX); |
524 SetLittle(Gear^.dX); |
545 Gear^.State:= Gear^.State or gstMoving or gstHHJumping; |
525 Gear^.State:= Gear^.State or gstMoving or gstHHJumping; |
546 end |
526 end |
547 else |
527 else |
548 exit; |
528 exit(false); |
549 |
529 |
550 jmpLJump: |
530 jmpLJump: |
551 begin |
531 begin |
552 if TestCollisionYwithGear(Gear, -1) <> 0 then |
532 if TestCollisionYwithGear(Gear, -1) <> 0 then |
553 if not TestCollisionXwithXYShift(Gear, _0, -2, hwSign(Gear^.dX)) then |
533 if not TestCollisionXwithXYShift(Gear, _0, -2, hwSign(Gear^.dX)) then |
581 if TestCollisionXwithGear(Gear, hwSign(Gear^.dX)) then SetLittle(Gear^.dX); |
561 if TestCollisionXwithGear(Gear, hwSign(Gear^.dX)) then SetLittle(Gear^.dX); |
582 Gear^.X:= Gear^.X + Gear^.dX; |
562 Gear^.X:= Gear^.X + Gear^.dX; |
583 inc(GoInfo.Ticks); |
563 inc(GoInfo.Ticks); |
584 Gear^.dY:= Gear^.dY + cGravity; |
564 Gear^.dY:= Gear^.dY + cGravity; |
585 if Gear^.dY > _0_4 then |
565 if Gear^.dY > _0_4 then |
586 exit; |
566 exit(false); |
587 if (Gear^.dY.isNegative) and (TestCollisionYwithGear(Gear, -1) <> 0) then |
567 if (Gear^.dY.isNegative) and (TestCollisionYwithGear(Gear, -1) <> 0) then |
588 Gear^.dY:= _0; |
568 Gear^.dY:= _0; |
589 Gear^.Y:= Gear^.Y + Gear^.dY; |
569 Gear^.Y:= Gear^.Y + Gear^.dY; |
590 if (not Gear^.dY.isNegative) and (TestCollisionYwithGear(Gear, 1) <> 0) then |
570 if (not Gear^.dY.isNegative) and (TestCollisionYwithGear(Gear, 1) <> 0) then |
591 begin |
571 begin |
592 Gear^.State:= Gear^.State and not (gstMoving or gstHHJumping); |
572 Gear^.State:= Gear^.State and not (gstMoving or gstHHJumping); |
593 Gear^.dY:= _0; |
573 Gear^.dY:= _0; |
594 case JumpType of |
574 case JumpType of |
595 jmpHJump: |
575 jmpHJump: |
596 if bY - hwRound(Gear^.Y) > 5 then |
576 if bY - hwRound(Gear^.Y) > 5 then |
597 begin |
577 begin |
598 HHJump:= true; |
|
599 GoInfo.JumpType:= jmpHJump; |
578 GoInfo.JumpType:= jmpHJump; |
600 inc(GoInfo.Ticks, 300 + 300) // 300 before jump, 300 after |
579 inc(GoInfo.Ticks, 300 + 300); // 300 before jump, 300 after |
601 end; |
580 exit(true) |
|
581 end; |
602 jmpLJump: |
582 jmpLJump: |
603 if abs(bX - hwRound(Gear^.X)) > 30 then |
583 if abs(bX - hwRound(Gear^.X)) > 30 then |
604 begin |
584 begin |
605 HHJump:= true; |
|
606 GoInfo.JumpType:= jmpLJump; |
585 GoInfo.JumpType:= jmpLJump; |
607 inc(GoInfo.Ticks, 300 + 300) // 300 before jump, 300 after |
586 inc(GoInfo.Ticks, 300 + 300); // 300 before jump, 300 after |
608 end |
587 exit(true) |
609 end; |
588 end |
610 exit |
589 end; |
611 end; |
590 exit(false) |
|
591 end; |
612 end; |
592 end; |
613 until false |
593 until false |
614 end; |
594 end; |
615 |
595 |
616 function HHGo(Gear, AltGear: PGear; var GoInfo: TGoInfo): boolean; |
596 function HHGo(Gear, AltGear: PGear; var GoInfo: TGoInfo): boolean; |
624 GoInfo.JumpType:= jmpNone; |
604 GoInfo.JumpType:= jmpNone; |
625 repeat |
605 repeat |
626 pX:= hwRound(Gear^.X); |
606 pX:= hwRound(Gear^.X); |
627 pY:= hwRound(Gear^.Y); |
607 pY:= hwRound(Gear^.Y); |
628 if pY + cHHRadius >= cWaterLine then |
608 if pY + cHHRadius >= cWaterLine then |
629 exit; |
609 exit(false); |
630 if (Gear^.State and gstMoving) <> 0 then |
610 if (Gear^.State and gstMoving) <> 0 then |
631 begin |
611 begin |
632 inc(GoInfo.Ticks); |
612 inc(GoInfo.Ticks); |
633 Gear^.dY:= Gear^.dY + cGravity; |
613 Gear^.dY:= Gear^.dY + cGravity; |
634 if Gear^.dY > _0_4 then |
614 if Gear^.dY > _0_4 then |
635 begin |
615 begin |
636 Goinfo.FallPix:= 0; |
616 Goinfo.FallPix:= 0; |
637 HHJump(AltGear, jmpLJump, GoInfo); // try ljump instead of fall with damage |
617 HHJump(AltGear, jmpLJump, GoInfo); // try ljump instead of fall with damage |
638 exit |
618 exit(false) |
639 end; |
619 end; |
640 Gear^.Y:= Gear^.Y + Gear^.dY; |
620 Gear^.Y:= Gear^.Y + Gear^.dY; |
641 if hwRound(Gear^.Y) > pY then |
621 if hwRound(Gear^.Y) > pY then |
642 inc(GoInfo.FallPix); |
622 inc(GoInfo.FallPix); |
643 if TestCollisionYwithGear(Gear, 1) <> 0 then |
623 if TestCollisionYwithGear(Gear, 1) <> 0 then |
645 inc(GoInfo.Ticks, 410); |
625 inc(GoInfo.Ticks, 410); |
646 Gear^.State:= Gear^.State and not (gstMoving or gstHHJumping); |
626 Gear^.State:= Gear^.State and not (gstMoving or gstHHJumping); |
647 Gear^.dY:= _0; |
627 Gear^.dY:= _0; |
648 HHJump(AltGear, jmpLJump, GoInfo); // try ljump instead of fall |
628 HHJump(AltGear, jmpLJump, GoInfo); // try ljump instead of fall |
649 HHGo:= true; |
629 HHGo:= true; |
650 exit |
630 exit(false) |
651 end; |
631 end; |
652 continue |
632 continue |
653 end; |
633 end; |
654 if (Gear^.Message and gmLeft )<>0 then |
634 if (Gear^.Message and gmLeft )<>0 then |
655 Gear^.dX:= -cLittle |
635 Gear^.dX:= -cLittle |
656 else |
636 else |
657 if (Gear^.Message and gmRight )<>0 then |
637 if (Gear^.Message and gmRight )<>0 then |
658 Gear^.dX:= cLittle |
638 Gear^.dX:= cLittle |
659 else |
639 else |
660 exit; |
640 exit(false); |
661 if TestCollisionXwithGear(Gear, hwSign(Gear^.dX)) then |
641 if TestCollisionXwithGear(Gear, hwSign(Gear^.dX)) then |
662 begin |
642 begin |
663 if not (TestCollisionXwithXYShift(Gear, _0, -6, hwSign(Gear^.dX)) |
643 if not (TestCollisionXwithXYShift(Gear, _0, -6, hwSign(Gear^.dX)) |
664 or (TestCollisionYwithGear(Gear, -1) <> 0)) then |
644 or (TestCollisionYwithGear(Gear, -1) <> 0)) then |
665 Gear^.Y:= Gear^.Y - _1; |
645 Gear^.Y:= Gear^.Y - _1; |