Ticket #1537: chasing.diff
File chasing.diff, 6.2 KB (added by , 10 years ago) |
---|
-
binaries/data/mods/public/simulation/components/UnitAI.js
1661 1661 var attackName = "attack_" + this.order.data.attackType.toLowerCase(); 1662 1662 this.SelectAnimation(attackName, false, 1.0, "attack"); 1663 1663 this.SetAnimationSync(prepare, this.attackTimers.repeat); 1664 this.StartTimer(prepare, this.attackTimers.repeat); 1664 // repeat timer faster than repeat time for the attack 1665 // as targets out-of-range also get detected in the timer loop 1666 // and the unit should respond fast to it to stop the animation in time 1667 this.StartTimer(prepare, Math.min(250,this.attackTimers.repeat)); 1665 1668 // TODO: we should probably only bother syncing projectile attacks, not melee 1666 1669 1667 1670 // If using a non-default prepare time, re-sync the animation when the timer runs. -
source/simulation2/components/CCmpUnitMotion.cpp
132 132 bool m_FormationController; 133 133 fixed m_WalkSpeed, m_OriginalWalkSpeed; // in metres per second 134 134 fixed m_RunSpeed, m_OriginalRunSpeed; 135 fixed m_TurnLength; 135 136 ICmpPathfinder::pass_class_t m_PassClass; 136 137 ICmpPathfinder::cost_class_t m_CostClass; 137 138 … … 297 298 m_WalkSpeed = m_OriginalWalkSpeed = paramNode.GetChild("WalkSpeed").ToFixed(); 298 299 m_Speed = m_WalkSpeed; 299 300 m_CurSpeed = fixed::Zero(); 301 m_TurnLength = fixed::Zero(); 300 302 301 303 if (paramNode.GetChild("Run").IsOk()) 302 304 m_RunSpeed = m_OriginalRunSpeed = paramNode.GetChild("Run").GetChild("Speed").ToFixed(); … … 350 352 351 353 serialize.NumberFixed_Unbounded("speed", m_Speed); 352 354 355 serialize.NumberFixed_Unbounded("turnLength", m_TurnLength); 356 353 357 serialize.Bool("moving", m_Moving); 354 358 serialize.Bool("facePointAfterMove", m_FacePointAfterMove); 355 359 … … 379 383 { 380 384 if (m_FormationController) 381 385 { 382 fixed dt= static_cast<const CMessageUpdate_MotionFormation&> (msg).turnLength;383 Move( dt);386 m_TurnLength = static_cast<const CMessageUpdate_MotionFormation&> (msg).turnLength; 387 Move(m_TurnLength); 384 388 } 385 389 break; 386 390 } … … 388 392 { 389 393 if (!m_FormationController) 390 394 { 391 fixed dt = static_cast<const CMessageUpdate_MotionUnit&> (msg).turnLength;392 Move( dt);395 m_TurnLength = static_cast<const CMessageUpdate_MotionFormation&> (msg).turnLength; 396 Move(m_TurnLength); 393 397 } 394 398 break; 395 399 } … … 535 539 536 540 void MoveSucceeded() 537 541 { 542 // No longer moving, so speed is 0. 543 m_CurSpeed = fixed::Zero(); 538 544 m_Moving = false; 539 545 540 546 CmpPtr<ICmpObstruction> cmpObstruction(GetEntityHandle()); … … 541 547 if (cmpObstruction) 542 548 cmpObstruction->SetMovingFlag(false); 543 549 544 // No longer moving, so speed is 0.545 m_CurSpeed = fixed::Zero();546 547 550 CMessageMotionChanged msg(false, false); 548 551 GetSimContext().GetComponentManager().PostMessage(GetEntityId(), msg); 549 552 } … … 995 998 } 996 999 else 997 1000 { 1001 // check if target was reached in case of a moving target 1002 CmpPtr<ICmpUnitMotion> cmpUnitMotion(GetSimContext(), m_TargetEntity); 1003 if 1004 ( 1005 cmpUnitMotion && 1006 cmpUnitMotion->IsMoving() && 1007 MoveToTargetRange(m_TargetEntity, m_TargetMinRange, m_TargetMaxRange) 1008 ) 1009 return; 1010 998 1011 // Not in formation, so just finish moving 999 1000 1012 StopMoving(); 1001 1013 1002 1003 1014 if (m_FacePointAfterMove) 1004 1015 FaceTowardsPointFromPos(pos, m_FinalGoal.x, m_FinalGoal.z); 1005 1016 // TODO: if the goal was a square building, we ought to point towards the … … 1313 1324 1314 1325 CFixedVector2D pos = cmpPosition->GetPosition2D(); 1315 1326 1327 entity_pos_t overShoot = fixed::Zero(); 1328 1329 // if the target is also moving, take an overshoot into account 1330 CmpPtr<ICmpUnitMotion> cmpUnitMotion(GetSimContext(), target); 1331 if (cmpUnitMotion && cmpUnitMotion->IsMoving()) 1332 overShoot = m_CurSpeed.Multiply(m_TurnLength); 1333 1334 entity_pos_t origMaxRange = maxRange; 1335 entity_pos_t origMinRange = minRange; 1336 maxRange -= overShoot; 1337 minRange += overShoot; 1338 if (maxRange < fixed::Zero() && origMaxRange >= fixed::Zero()) 1339 maxRange = fixed::Zero(); 1340 if (maxRange > fixed::Zero() && minRange > maxRange) 1341 minRange = maxRange; 1342 1316 1343 ICmpPathfinder::Goal goal; 1317 1344 1318 1345 if (minRange.IsZero() && maxRange.IsZero()) … … 1381 1408 m_State = STATE_INDIVIDUAL_PATH; 1382 1409 m_TargetEntity = target; 1383 1410 m_TargetOffset = CFixedVector2D(); 1384 m_TargetMinRange = minRange;1385 m_TargetMaxRange = maxRange;1411 m_TargetMinRange = origMinRange; 1412 m_TargetMaxRange = origMaxRange; 1386 1413 m_FinalGoal = goal; 1387 1414 1388 1415 BeginPathing(pos, goal); … … 1457 1484 bool CCmpUnitMotion::MoveToTargetRange(entity_id_t target, entity_pos_t minRange, entity_pos_t maxRange) 1458 1485 { 1459 1486 PROFILE("MoveToTargetRange"); 1487 entity_pos_t overShoot = fixed::Zero(); 1460 1488 1489 // if the target is als moving, take an overshoot into account 1490 CmpPtr<ICmpUnitMotion> cmpUnitMotion(GetSimContext(), target); 1491 if (cmpUnitMotion && cmpUnitMotion->IsMoving()) 1492 overShoot = m_CurSpeed.Multiply(m_TurnLength); 1493 1494 entity_pos_t origMaxRange = maxRange; 1495 entity_pos_t origMinRange = minRange; 1496 maxRange -= overShoot; 1497 minRange += overShoot; 1498 if (maxRange < fixed::Zero() && origMaxRange >= fixed::Zero()) 1499 maxRange = fixed::Zero(); 1500 if (maxRange > fixed::Zero() && minRange > maxRange) 1501 minRange = maxRange; 1502 1461 1503 CmpPtr<ICmpPosition> cmpPosition(GetEntityHandle()); 1462 1504 if (!cmpPosition || !cmpPosition->IsInWorld()) 1463 1505 return false; … … 1578 1620 m_State = STATE_INDIVIDUAL_PATH; 1579 1621 m_TargetEntity = target; 1580 1622 m_TargetOffset = CFixedVector2D(); 1581 m_TargetMinRange = minRange;1582 m_TargetMaxRange = maxRange;1623 m_TargetMinRange = origMinRange; 1624 m_TargetMaxRange = origMaxRange; 1583 1625 m_FinalGoal = goal; 1584 1626 1585 1627 BeginPathing(pos, goal); … … 1596 1638 1597 1639 CFixedVector2D targetPos = cmpTargetPosition->GetPosition2D(); 1598 1640 1599 return MoveToPointRange(targetPos.X, targetPos.Y, minRange, maxRange, target);1641 return MoveToPointRange(targetPos.X, targetPos.Y, origMinRange, origMaxRange, target); 1600 1642 } 1601 1643 } 1602 1644