Metadata-Version: 2.4
Name: nav-sim2d
Version: 0.0.1
Summary: Educational library of 2D simulation for mobile robot navigation.
Author: Elias J. R. Freitas
Requires-Python: >=3.10
Description-Content-Type: text/markdown
Requires-Dist: pygame>=2.5.0
Requires-Dist: pygame_gui>=0.6.9
Requires-Dist: numpy>=1.24
Requires-Dist: PyYAML>=6.0

# Nav Sim

A lightweight 2D simulation framework for mobile robot navigation using **Pygame**, with support for sensors, external controllers, and interactive visualization.

---

## Supported Robot Models

- `holonomic`  
  Command:
  ```python
  {"vx": ..., "vy": ...}
  ```

- `differential`  
  Command:
  ```python
  {"v": ..., "omega": ...}
  ```

- `ackermann`  
  Command:
  ```python
  {"speed": ..., "steer": ...}
  ```

---

## 🧠 Architecture

The simulator follows a modular design:

- ✅ **Simulator (`nav_sim`)**  
  Handles physics, rendering, environment, and sensors

- ✅ **External Controllers**  
  Implement navigation strategies (APF, Vortex, etc.)

> Controllers are not part of the core library. They live in `examples/` or in the user’s project.

---

## 📡 Sensors

### LiDAR (2D)

The simulator provides a configurable 2D LiDAR:

- Angular scan
- Range-limited
- Returns:

```python
(angle, distance, hit_point)
```

- Passed to controllers as:

```python
lidar_readings
```

---

## ⚙️ Installation

```bash
python -m venv .venv

# Linux / macOS
source .venv/bin/activate  

# Windows
.venv\Scripts\activate

pip install -r requirements.txt
```

---

## ▶️ Run Examples

```bash
python examples/run_holonomic.py
python examples/run_differential.py
python examples/run_ackermann.py
```

---

## 🧪 Basic Usage

```python
from pathlib import Path
from nav_sim import Simulator, load_config
from examples.controllers.potential_field import potential_field_controller

config = load_config(Path("config/default.yaml"))
config["robot"]["type"] = "differential"

sim = Simulator(
    config=config,
    controller=potential_field_controller
)

sim.run()
```

---

## 🧩 Controller Interface

```python
def controller(robot, world, goal, config, dt, lidar_readings=None) -> dict:
    ...
```

### Parameters

- `robot` → robot state (position, heading, limits)
- `world` → obstacle representation
- `goal` → current waypoint
- `config` → YAML configuration
- `dt` → simulation timestep
- `lidar_readings` → sensor data

---

## 🧠 Artificial Potential Fields (APF)

This project includes a classical APF implementation based on Khatib’s method:

### Total force

F(q) = F_att(q) + F_rep(q)

### Attractive force

F_att = k_att (q_goal - q)

### Repulsive force

F_rep,i = k_r (1/d_i - 1/d_s) (1/d_i^2) r_hat_i

Where:

- d_i → LiDAR distance corrected by robot radius  
- d_s → influence distance  
- r_hat_i → unit vector away from obstacle  

---

## 🛑 Collision Handling

The simulator detects collisions using:

    d <= r_robot + r_obstacle

### Behavior

- The robot stops immediately
- A visual indicator (💥) is displayed

---

## 🎨 Custom Drawing

You can extend visualization with:

```python
def custom_draw(sim, screen):
    ...
```

Usage:

```python
sim = Simulator(
    config=config,
    controller=controller,
    draw_callback=custom_draw
)
```

---

## 🖱️ User Interaction

- Left click → add waypoint
- Right click → add obstacle
- Scroll → zoom
- Middle button + drag → pan

### GUI

- Center Camera → reset view
- Reset → restart simulation

---

## ✅ Features

- ✅ Multiple robot models
- ✅ 2D LiDAR sensor
- ✅ External controllers
- ✅ Artificial Potential Fields (APF)
- ✅ Collision detection with geometry
- ✅ Custom rendering
- ✅ Real-time interaction

---

## 🚀 Roadmap

- Vortex APF
- Harmonic (Laplace) fields
- Local minima avoidance
- Advanced visualization

---

## 📄 License

Free for educational and research use.
