logo
Kurashizu Blogwhere ideas flow
  • Home
  • News
  • Blog
  • About
  • Home
  • News
  • Blog
  • About

© 2026 Kurashizu. All rights reserved.

Admin·New Post·Service Status
Powered by Cloudflare·30.10.26
← Back to news

2D Vehicles

Original article
patkerr.co.uk|582 points|112 comments|by Michelangelo11|Oct 7, 2026

2D Vehicles: A Project Retrospective (1996–2026)

During a single weekend in late August 1996, I developed a 2D physics simulation. This experiment eventually served as the foundation for the vehicle mechanics in the globally recognized title Grand Theft Auto (GTA).

The project originated as a simple wireframe demonstration coded in GFA BASIC on an Atari ST. For the commercial release of the game, this logic was ported to C. To celebrate the 30th anniversary of this system, I have created a remastered version using JavaScript, allowing anyone to experience the original logic in a polished format.

🎮 User Guide

The simulation is playable via the browser, featuring touch-screen support for mobile users.

Mode Selection

You can toggle between three distinct vehicle types using the Settings menu or the following keyboard shortcuts:

  1. Car: The standard vehicle mode.
  2. Ship: A technically simpler model.
  3. Brick: The most basic physics object.

Control Mapping

KeyActionDescription
BBarriersToggles the collision walls around the play area.
GGravityToggles vertical gravity (best experienced in Ship or Brick modes).
ZDead ZoneToggles the camera's "dead zone" (the distance a vehicle moves before the camera follows).
XDynamic ZoomToggles speed-based zooming, where the camera pulls back as velocity increases.

VOLUNTARY DISCLAIMER: This recreation is a wholly independent work. It is not affiliated with, endorsed by, or connected to the "Grand Theft Auto" franchise, its publisher "Take-Two", or the developer "Rockstar Games".


🛠️ Technical Evolution

The prototype was built by combining a general 2D rigid body with a simplified car model. The development progressed in stages: Brick →\rightarrow→ Ship (inspired by the 1986 classic Thrust) →\rightarrow→ Car.

The Physics Core

At its heart, the system utilizes a classical 2D rigid body dynamics simulation. At the time, this was an uncommon approach in game development; most titles relied on basic high-school "point physics": F=maF = maF=ma These older methods often used "wonky hacks" to simulate rotation. By implementing proper rigid-body physics—specifically including torques—rotation is handled with far more coherence.

The Vehicle Layer

On top of the core physics, I implemented a "novel" simulation layer to mimic tyre behavior. While I recognized that my model was technically incorrect and physically approximate, it was good enough to create the desired feel.

Physics Diagram Placeholder

⚙️ System Architecture

The JavaScript recreation separates concerns to ensure clarity between input, logic, and visuals.

One Body, Three Behaviors

A vehicle is composed of three elements: a Rigid Body, a Shell (defining shape and collision), and a Dynamics Object (defining behavior).

  • The Brick: Responds to forces generated by pointer dragging.
  • The Ship: Applies thrust from a specific attachment point.
  • The Car: Implements engine force and steering, with resistance calculated at four distinct tyre points.

When the user switches modes, the system swaps the shell and behavior while maintaining the current position and momentum of the body.

📐 Mechanics of Motion

The rigid body tracks four primary variables:

  • Position & Velocity
  • Angle & Angular Velocity

A force applied directly through the center of mass alters linear motion, whereas a force applied offset from the center generates torque, causing the body to spin.

Collision Handling

The simulation uses a simple barrier solver rather than a complex general collision system.

  1. If a shape crosses a boundary, it is pushed back inside.
  2. A contact impulse is applied based on the entry velocity.
  3. Because edges are frictionless, an off-center hit will change both the vehicle's trajectory and its spin.
// Conceptual Physics Update Loop
function update(dt) {
    let totalForce = dynamics.calculateForces();
    let totalTorque = dynamics.calculateTorque();
    
    velocity += (totalForce / mass) * dt;
    angularVelocity += (totalTorque / inertia) * dt;
    
    position += velocity * dt;
    angle += angularVelocity * dt;
}

🏎️ The Approximate Tyre Model

The "Car" mode calculates the velocity at each tyre's position and splits it into two vectors:

  • Longitudinal: Along the wheel's heading.
  • Lateral: Sideways across the wheel.

The simulation then applies resistance:

  • Rolling: Low resistance.
  • Sideways: High resistance (simulating grip).

Special Behaviors:

  • Steering: Rotates the front wheels' headings, redirecting the resulting forces to turn the car.
  • Handbrake: Increases rear rolling resistance while simultaneously reducing rear lateral grip.

These forces are proportional to velocity without a maximum cap. This is effectively a damping model rather than a realistic simulation of friction or slip, but it successfully mimics the feeling of tyres resisting sideways slides.

🏁 Final Integration

The Vehicle Coordinator manages the lifecycle of the simulation:

  • Request forces from the active dynamics object.
  • Advance the rigid body state.
  • Transform shell local points into world coordinates for the renderer.
  • Resolve barrier contacts.

To prevent "artificial spin" (which occurs when a single corner hits a wall), the system identifies the flat face touching the barrier and calculates the impulse based on the midpoint of the contacting points.