# How Human Movement Affects Wi-Fi CSI Signals: A Technical Analysis of the wifi-densepose Repository

> Discover how human movement impacts Wi-Fi CSI signals. The wifi-densepose repository analyzes alterations in amplitude, phase, and frequency-domain characteristics caused by body movement.

- Repository: [rUv/wifi-densepose](https://github.com/ruvnet/wifi-densepose)
- Tags: deep-dive
- Published: 2026-02-19

---

**When humans move through a Wi-Fi environment, they alter multipath propagation paths, causing measurable variations in Channel State Information (CSI) amplitude, phase, and frequency-domain characteristics that the wifi-densepose pipeline detects through statistical feature extraction and temporal analysis.**

Human movement detection through walls and obstacles using commodity Wi-Fi hardware relies on capturing subtle changes in Channel State Information (CSI). The open-source **wifi-densepose** repository (`ruvnet/wifi-densepose`) implements a complete pipeline that demonstrates how human movement affects Wi-Fi CSI signals by processing raw IQ samples into motion confidence scores and spatial features.

## The Physics of Movement in Wi-Fi Channels

Wi-Fi CSI captures the complex-valued channel response for every sub-carrier, antenna pair, and transmit-receive combination. When a person moves, their body blocks, reflects, and scatters radio frequency signals, dynamically altering the multipath propagation environment. These physical changes manifest as **amplitude attenuation**, **phase shifts**, and **Doppler frequency shifts** across the CSI stream, creating a unique signature that distinguishes human motion from static environmental noise.

## CSI Processing Pipeline Architecture

The wifi-densepose codebase processes these signal variations through a modular pipeline defined in [`v1/src/core/csi_processor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/csi_processor.py). Raw bytes from ESP32 or router hardware flow through phase sanitization, noise removal, and feature extraction stages to produce a human detection confidence score.

The pipeline executes these sequential operations:

1. **Raw extraction** ([`csi_extractor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/csi_extractor.py)): Captures byte streams from Wi-Fi hardware.
2. **Phase sanitization** ([`phase_sanitizer.py`](https://github.com/ruvnet/wifi-densepose/blob/main/phase_sanitizer.py)): Unwraps phase discontinuities via `sanitize_phase` and removes outliers.
3. **Pre-processing** (`CSIProcessor._remove_noise`, `_apply_windowing`, `_normalize_amplitude`): Conditions the signal for analysis.
4. **Feature extraction** (`_extract_amplitude_features`, `_extract_phase_features`, `_extract_correlation_features`, `_extract_doppler_features`): Computes statistical descriptors.
5. **Motion analysis** (`_analyze_motion_patterns`): Derives a composite motion score from variance and correlation deviation.
6. **Confidence calculation** (`_calculate_detection_confidence`, `_apply_temporal_smoothing`): Produces the final detection result.

## How Movement Manifests in CSI Features

### Amplitude Variance Across Sub-Carriers

Human bodies block specific propagation paths, causing time-varying attenuation in certain sub-carriers. The `_extract_amplitude_features` method in [`v1/src/core/csi_processor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/csi_processor.py) quantifies this effect by computing `amplitude_variance = np.var(csi_data.amplitude, axis=0)`, capturing the temporal instability introduced by moving scatterers.

### Phase Differences Between Adjacent Sub-Carriers

As a person moves, changing path lengths introduce phase shifts that differ across the frequency spectrum. The pipeline calculates this via `np.diff(csi_data.phase, axis=1)` in `_extract_phase_features`, averaging the differential phase response to detect motion-induced path length variations.

### Antenna Correlation Degradation

Static environments maintain stable spatial correlation between multiple antennas. Human movement disrupts this correlation by introducing independent scattering at different antenna elements. The `_extract_correlation_features` method computes `np.corrcoef(csi_data.amplitude)` to measure this spatial decorrelation.

### Doppler Frequency Shifts

Relative motion between the human body and Wi-Fi transceivers creates Doppler-shifted reflections visible in the power spectral density. The `_extract_doppler_features` method computes these frequency-domain characteristics using FFT-based PSD analysis, providing a placeholder Doppler vector for motion frequency analysis.

### Motion Pattern Analysis and Detection Confidence

The system synthesizes these indicators into a **motion-score** within `_analyze_motion_patterns`. This weighted combination of amplitude variance and correlation deviation feeds into `_calculate_detection_confidence`, which applies `_apply_temporal_smoothing` to reduce false positives. When the confidence exceeds the configurable `human_detection_threshold` (default **0.8**), the pipeline returns a `HumanDetectionResult` with `human_detected=True`.

## Implementing the Detection Pipeline

The following example demonstrates the complete workflow from raw hardware bytes to human presence detection:

```python
from src.hardware.csi_extractor import CSIExtractor
from src.core.phase_sanitizer import PhaseSanitizer
from src.core.csi_processor import CSIProcessor

# 1️⃣  Extract raw CSI (mocked in tests)

extractor = CSIExtractor(
    config={'hardware_type': 'esp32', 'sampling_rate': 100, 'buffer_size': 256,
            'timeout': 1.0}, logger=None
)
raw_csi = extractor._read_raw_data()                     # → bytes from ESP32

# 2️⃣  Parse into structured CSIData

csi_data = extractor.parser.parse(raw_csi)

# 3️⃣  Sanitize phase

phase_sanitizer = PhaseSanitizer(
    config={'unwrapping_method': 'numpy', 'outlier_threshold': 3.0,
            'smoothing_window': 5}, logger=None
)
csi_data.phase = phase_sanitizer.sanitize_phase(csi_data.phase)

# 4️⃣  Process and detect human presence

processor = CSIProcessor(
    config={'sampling_rate': 100, 'window_size': 256, 'overlap': 0.5,
            'noise_threshold': -80, 'human_detection_threshold': 0.8},
    logger=None
)
result = await processor.process_csi_data(csi_data)

print(f"Human detected: {result.human_detected} (confidence {result.confidence:.2f})")

```

After processing, inspect the specific features that indicate movement:

```python
features = processor.extract_features(csi_data)
print("Amplitude variance per sub‑carrier:", features.amplitude_variance[:5])
print("Mean phase difference:", features.phase_difference)
print("Correlation matrix shape:", features.correlation_matrix.shape)
print("Doppler placeholder vector:", features.doppler_shift[:3])

```

Adjust detection sensitivity by modifying the processor configuration:

```python
processor.human_detection_threshold = 0.6   # more sensitive

processor.smoothing_factor = 0.7          # smoother confidence curve

```

## Critical Source Files

- [`v1/src/hardware/csi_extractor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/hardware/csi_extractor.py): Low-level parser for ESP32 and router CSI byte streams.
- [`v1/src/core/phase_sanitizer.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/phase_sanitizer.py): Implements phase unwrapping via `unwrap_phase` and outlier removal via `remove_outliers` to handle phase wraps caused by rapid motion.
- [`v1/src/core/csi_processor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/csi_processor.py): Contains the full processing pipeline including feature extraction methods and the motion pattern analysis logic.
- [`v1/src/models/modality_translation.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/models/modality_translation.py): Translates CSI amplitude and sanitized phase into spatial feature maps for DensePose networks.
- [`v1/references/wifi_densepose_pytorch.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/references/wifi_densepose_pytorch.py): End-to-end PyTorch model consuming spatial features for pose estimation.

## Summary

- Human movement alters Wi-Fi multipath propagation, creating detectable variations in CSI **amplitude**, **phase**, and **correlation** structures.
- The **wifi-densepose** pipeline processes these changes through `PhaseSanitizer` for signal conditioning and `CSIProcessor` for statistical feature extraction.
- Key detection features include **amplitude variance**, **differential phase**, **antenna correlation matrices**, and **Doppler characteristics**.
- The system calculates a composite **motion-score** combining variance and correlation deviation, applying temporal smoothing to generate a confidence score.
- Detection triggers when confidence exceeds the `human_detection_threshold` (default 0.8), as implemented in [`v1/src/core/csi_processor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/csi_processor.py).

## Frequently Asked Questions

### What specific CSI features indicate human movement?

Human movement primarily affects **amplitude variance** across sub-carriers, **phase differences** between adjacent frequencies, and **spatial correlation** between antenna streams. The wifi-densepose code extracts these via `np.var()` for amplitude instability, `np.diff()` for phase gradients, and `np.corrcoef()` for antenna decorrelation in [`v1/src/core/csi_processor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/csi_processor.py).

### How does the repository handle noisy phase data?

The `PhaseSanitizer` class in [`v1/src/core/phase_sanitizer.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/phase_sanitizer.py) applies **phase unwrapping** via `unwrap_phase` to resolve discontinuities, **outlier removal** via `remove_outliers` using a configurable threshold (default 3.0), and optional smoothing windows to eliminate high-frequency noise introduced by rapid motion.

### What is the default detection threshold for human presence?

The `CSIProcessor` uses a default `human_detection_threshold` of **0.8**, configurable during initialization or runtime. Values closer to 0.6 increase sensitivity for small movements but may introduce false positives, while higher values reduce false alarms at the cost of missing subtle motions.

### Can this system distinguish between multiple moving people?

The current implementation in [`v1/src/core/csi_processor.py`](https://github.com/ruvnet/wifi-densepose/blob/main/v1/src/core/csi_processor.py) calculates a single composite motion score without spatial localization of multiple scatterers. While the correlation features and Doppler analysis theoretically contain information about multiple moving objects, the repository's `_analyze_motion_patterns` method aggregates these into a binary detection decision rather than individual tracking.