Hit Physics

In short

HitPhysics.Simulate runs the whole flight up front in 1/60 s steps. The game then just replays the recorded path. In the air the ball curves (hook or slice) and weak contact falls a little faster. A home run crosses the outfield wall above its height, inside the foul poles, before it first lands. Fair or foul is where the ball actually goes, so a ball can start fair and hook foul. Distance is carry: where it first touches down.

How it works

  1. Launch. The velocity comes from the swing’s exit velocity (mph), launch angle and spray angle. See Batting Explained.
  2. Each step (1/60 s, up to 14 s):
    • Drag: acceleration = -Drag x |v - wind| x (v - wind). Drag and wind act in every phase, so wind keeps pushing a rolling ball.
    • Gravity, unless rolling. Until the first landing it is multiplied by the swing’s gravityScale (x1 perfect, x1.05 nice, x1.15 sour), and the hit’s curve acts: curveAccel sideways to the direction it was sent (+ = toward right field), plus a quarter of its size pulling the ball back toward the plate.
    • Scoreboard: crossing the scoreboard’s face inside its frame punches a hole. The ball bounces back almost dead. See Scoreboard Smash.
    • Outfield wall: checked as the ball crosses the wall distance for its current direction (only within +/-45 degrees). Above the wall and still on the fly = cleared (home run). Below the top = carom back off the wall (and hitWall if it hadn’t landed yet).
    • Stands: solid steps. A ball running into a higher step’s front rebounds like off the wall; a ball that rolls off a step falls again.
    • Floor (grass or a step top): the first touch records the landing point. Fast impacts bounce; slow ones settle into a roll with friction until the ball stops.
  3. Results: distanceFt (carry to the first landing), totalDistanceFt (to rest), maxHeightFt, bounces, isHomeRun = clearedWall, isFair = clearedWall or |spray of the landing point| <= 45, and for a home run the best target it earned (see Scoring).

HitOutcome also offers LandingTime, PathSeconds and PositionAt(sinceContact), used by the Hit Show and the replays.

The curve

HitTables.CurveAccel sets the sideways pull: 2.4 m/s^2 x zone (1 / 0.6 / 0.3) x lift fade x side x batter curve. High flies curve less (full below 33.75 degrees of launch, none at 78.75). Side is the held A/D direction at full strength, or, left alone, it bends away from a neutral line 8.4 degrees to the pull side, more the further from it. The code comment says perfect-zone hits bend about 3 to 5 degrees by the time they land, twice that with a super-curve batter. Hand-built swings (tests, the Dev menu bat, cutscenes) have no curve.

Park environment

BallparkDefinition.GetEnvironment() gives:

  • gravity = down x 9.81 x gravityScale (low gravity on the moon).
  • wind = direction x windMph x 0.44704 m/s. windDirectionDeg is where the wind blows toward: 0 = out to centre, -45 = out to left, 180 = straight in.

Per-park values (wall distances, wall height, wind, gravity): see Ballparks and each park note.

Coordinates

Home plate is the origin, +Z points to centre field, -X is left field. Spray angle: -45 = left field line, 0 = centre, +45 = right field line (BallparkMath).

Numbers

WhatValueWhere to tune
Drag coefficient0.0042 (comment: a perfect 106 mph / 28 degree swing carries about 415 ft)HitPhysics.Drag
Time step / max time1/60 s / 14 sTimeStep, MaxSeconds
Ball radius0.037 mHitPhysics.BallRadius
Curve back toward the plate0.25 of the curveHitPhysics.CurveTowardPlate
Curve strength2.4 m/s^2 at fullHitTables.CurveScale
Extra gravity in flightx1 / x1.05 / x1.15 (perfect / nice / sour)HitTables.GravityScale
Grass bounce: vertical kept0.45GroundRestitution
Grass bounce: horizontal kept0.62BounceFriction
Slower impacts than this roll1.2 m/sMinBounceSpeed
Rolling friction0.6 x gravityRollingFriction
Stop speed0.25 m/sStopSpeed
Wall / step reboundrestitution 0.4, friction 0.8WallRestitution, WallFriction
Scoreboard reboundrestitution 0.15, friction 0.35BoardRestitution, BoardFriction
Fair territorywithin +/-45 degreesHitPhysics.FoulLineDeg
Base gravity9.81 m/s^2 x gravityScaleBallparkDefinition.GetEnvironment
Unit conversions1 mph = 0.44704 m/s, 1 ft = 0.3048 m, 1 m = 3.28084 ftBallparkMath

In the code

FileWhat it does
Assets/_Project/Scripts/Batting/HitPhysics.csHitOutcome (path, landing, flags, score, PositionAt) and Simulate
Assets/_Project/Scripts/Batting/HitTables.csCurveAccel, GravityScale
Assets/_Project/Scripts/Ballparks/BallparkMath.csUnit conversions, PolarToWorld, DistanceFt, SprayAngle, FlightEnvironment
Assets/_Project/Scripts/Data/BallparkDefinition.csGetEnvironment, WallDistanceFt, wind and gravity fields
Assets/_Project/Scripts/Ballparks/StadiumLayout.csSurfaceHeight: the stands’ steps as a floor
Assets/_Project/Scripts/Ballparks/Scoreboard.csFace: where the scoreboard is

Gotchas

  • Fair or foul is decided by the path, not the launch spray: the curve or the wind can carry a ball foul (or back fair). A home run is any ball over the wall inside the poles.
  • The curve and extra gravity stop at the first landing; bounces and rolls use normal gravity.
  • A ball that clears the wall after a bounce is still in play (an out), not a home run.
  • If the ball smashes the scoreboard on the fly, its distance is at least the distance to the scoreboard point, though it drops short.
  • If the 14 s run out before the ball lands, the last point counts as the landing.
  • In co-op, spectators run the same simulation for the picture (the result message carries zone, aim, curve and gravity so the path matches), but the home run, fair flag, distance and score are overwritten with the batter’s own result. See Live Spectating.