Warp Tunnel
Source: src/warp_tunnel.c · 154 lines · 8 functions.
Screen / module overview
- Start the tunnel
Randomise 72 stars beyond the central opening. Select initial speed and white theme.
- Handle controls
Reset stars, cycle colour theme or change speed as requested.
- Update when 25 ms has elapsed
Cap elapsed time at 50 ms. Increase each star depth, with speed increasing as it moves outward.
- Recycle stars
When a star exceeds the tunnel radius, return it near the central opening.
- Draw and repeat
Clear black. Draw coloured streaks, clipping their tails to keep the central opening empty. Briefly show changed controls.
Module entry points
These functions are exposed to the rest of the project. Open one to follow its decisions and the helpers it calls.
How to read these diagrams
Each function has its own expandable diagram using the actual expressions and statements from this file. Decisions split into True and False; loop bodies are indented. Returns end the function immediately; break and continue follow their C meanings. Arrows between statements show their order when execution reaches them.
These are structural source diagrams before preprocessing, not runtime traces. Conditional compilation and macros remain source expressions. Ternary choices remain inside their statement. Calls are linked separately; callback execution and task scheduling are not inferred.
Functions in this file
resetStar() · source line 56
static void resetStar(warp_star_t *star, bool spread_out)
- Execute
star->angle = (float)(esp_random() % 6284U) * WARP_PI / 3142.0f; - Execute
star->depth = spread_out ? WARP_CENTRE_EMPTY_RADIUS + (float)(esp_random() % 12000U) / 100.0f : WARP_CENTRE_EMPTY_RADIUS + (float)(esp_random() % 1600U) / 100.0f; - Execute
star->colour = (uint8_t)(esp_random() % WARP_THEME_COLOURS);
Read original function source
static void resetStar(warp_star_t *star, bool spread_out)
{
star->angle = (float)(esp_random() % 6284U) * WARP_PI / 3142.0f;
// All stars start beyond the central opening, keeping that area empty.
star->depth = spread_out ? WARP_CENTRE_EMPTY_RADIUS +
(float)(esp_random() % 12000U) / 100.0f :
WARP_CENTRE_EMPTY_RADIUS +
(float)(esp_random() % 1600U) / 100.0f;
star->colour = (uint8_t)(esp_random() % WARP_THEME_COLOURS);
}resetStars() · source line 67
static void resetStars(bool spread_out)
Calls into this documentation:
- FOR loop
unsigned index = 0U; index < WARP_STAR_COUNT; ++indexRepeat body while the loop condition permits; then continue below.
- Execute
resetStar(&stars[index], spread_out);
Read original function source
static void resetStars(bool spread_out)
{
for (unsigned index = 0U; index < WARP_STAR_COUNT; ++index) {
resetStar(&stars[index], spread_out);
}
}starPosition() · source line 74
static void starPosition(const warp_star_t *star, float depth, int *x, int *y)
- Execute
*x = WARP_CENTRE_X + (int)lroundf(cosf(star->angle) * depth); - Execute
*y = WARP_CENTRE_Y + (int)lroundf(sinf(star->angle) * depth * WARP_VERTICAL_SCALE);
Read original function source
static void starPosition(const warp_star_t *star, float depth, int *x, int *y)
{
*x = WARP_CENTRE_X + (int)lroundf(cosf(star->angle) * depth);
*y = WARP_CENTRE_Y + (int)lroundf(sinf(star->angle) * depth * WARP_VERTICAL_SCALE);
}startWarpTunnel() · source line 80
void startWarpTunnel(uint32_t now_ms)
Calls into this documentation:
- Execute
resetStars(true); - Execute
last_update_ms = now_ms; - Execute
controls_changed_at = now_ms; - Execute
speed_index = 1U; - Execute
theme_index = 0U; - Execute
reset_changed = false; - Execute
theme_changed = false; - Execute
running = true;
Read original function source
void startWarpTunnel(uint32_t now_ms)
{
resetStars(true);
last_update_ms = now_ms;
controls_changed_at = now_ms;
speed_index = 1U;
theme_index = 0U;
reset_changed = false;
theme_changed = false;
running = true;
}stopWarpTunnel() · source line 92
void stopWarpTunnel(void)
- Execute
running = false;
Read original function source
void stopWarpTunnel(void)
{
running = false;
}warpTunnelAction() · source line 97
void warpTunnelAction(bool reset, bool next_theme, bool next_speed, uint32_t now_ms)
Calls into this documentation:
- Decision
!runningTrue- Exit this function
return;
FalseContinue after this decision.
- Decision
resetTrue- Execute
resetStars(true);
FalseContinue after this decision.
- Decision
next_themeTrue- Execute
theme_index = (uint8_t)((theme_index + 1U) % WARP_THEME_COUNT);
FalseContinue after this decision.
- Decision
next_speedTrue- Execute
speed_index = (uint8_t)((speed_index + 1U) % WARP_SPEED_COUNT);
FalseContinue after this decision.
- Decision
!reset && !next_theme && !next_speedTrue- Exit this function
return;
FalseContinue after this decision.
- Execute
reset_changed = reset; - Execute
theme_changed = next_theme && !reset; - Execute
controls_changed_at = now_ms;
Read original function source
void warpTunnelAction(bool reset, bool next_theme, bool next_speed, uint32_t now_ms)
{
if (!running) return;
if (reset) resetStars(true);
if (next_theme) theme_index = (uint8_t)((theme_index + 1U) % WARP_THEME_COUNT);
if (next_speed) speed_index = (uint8_t)((speed_index + 1U) % WARP_SPEED_COUNT);
if (!reset && !next_theme && !next_speed) return;
reset_changed = reset;
theme_changed = next_theme && !reset;
controls_changed_at = now_ms;
}updateWarpTunnel() · source line 109
void updateWarpTunnel(uint32_t now_ms)
Calls into this documentation:
- Decision
!running || now_ms - last_update_ms < WARP_FRAME_MSTrue- Exit this function
return;
FalseContinue after this decision.
- Execute
uint32_t elapsed_ms = now_ms - last_update_ms; - Decision
elapsed_ms > 50UTrue- Execute
elapsed_ms = 50U;
FalseContinue after this decision.
- Execute
last_update_ms = now_ms; - Execute
const float elapsed = (float)elapsed_ms / 1000.0f * speed_multipliers[speed_index]; - FOR loop
unsigned index = 0U; index < WARP_STAR_COUNT; ++indexRepeat body while the loop condition permits; then continue below.
- Execute
warp_star_t *star = &stars[index]; - Execute
star->depth += (35.0f + star->depth * 1.15f) * elapsed; - Decision
star->depth > WARP_RADIUSTrue- Execute
resetStar(star, false);
FalseContinue after this decision.
Read original function source
void updateWarpTunnel(uint32_t now_ms)
{
if (!running || now_ms - last_update_ms < WARP_FRAME_MS) return;
uint32_t elapsed_ms = now_ms - last_update_ms;
if (elapsed_ms > 50U) elapsed_ms = 50U;
last_update_ms = now_ms;
const float elapsed = (float)elapsed_ms / 1000.0f * speed_multipliers[speed_index];
for (unsigned index = 0U; index < WARP_STAR_COUNT; ++index) {
warp_star_t *star = &stars[index];
star->depth += (35.0f + star->depth * 1.15f) * elapsed;
if (star->depth > WARP_RADIUS) resetStar(star, false);
}
}drawWarpTunnel() · source line 123
void drawWarpTunnel(uint16_t *frame)
Calls into this documentation:
- Decision
!running || frame == NULLTrue- Exit this function
return;
FalseContinue after this decision.
- Execute
clear(frame, COLOR_BLACK); - FOR loop
unsigned index = 0U; index < WARP_STAR_COUNT; ++indexRepeat body while the loop condition permits; then continue below.
- Execute
const warp_star_t *star = &stars[index]; - Decision
star->depth <= WARP_CENTRE_EMPTY_RADIUSTrue- Next loop iteration
continue;
FalseContinue after this decision.
- Execute
const float tail_depth = fmaxf(star->depth * 0.76f, WARP_CENTRE_EMPTY_RADIUS); - Execute
int tail_x; - Execute
int tail_y; - Execute
int head_x; - Execute
int head_y; - Execute
starPosition(star, tail_depth, &tail_x, &tail_y); - Execute
starPosition(star, star->depth, &head_x, &head_y); - Execute
draw_line(frame, tail_x, tail_y, head_x, head_y, theme_colours[theme_index][star->colour]);
- Decision
last_update_ms - controls_changed_at < WARP_STATUS_MSTrue- Execute
char text[20]; - Decision
reset_changedTrue- Execute
snprintf(text, sizeof(text), "A WARP RESET");
False- Decision
theme_changedTrue- Execute
snprintf(text, sizeof(text), "C %s", theme_names[theme_index]);
False- Execute
snprintf(text, sizeof(text), "E SPEED %u", (unsigned)(speed_index + 1U));
- Execute
draw_text_centred(frame, WARP_CENTRE_X, 155, text, 1, COLOR_LIGHTGREY);
FalseContinue after this decision.
Read original function source
void drawWarpTunnel(uint16_t *frame)
{
if (!running || frame == NULL) return;
clear(frame, COLOR_BLACK);
for (unsigned index = 0U; index < WARP_STAR_COUNT; ++index) {
const warp_star_t *star = &stars[index];
if (star->depth <= WARP_CENTRE_EMPTY_RADIUS) continue;
// Clip the streak at the opening rather than allowing its tail into it.
const float tail_depth = fmaxf(star->depth * 0.76f, WARP_CENTRE_EMPTY_RADIUS);
int tail_x;
int tail_y;
int head_x;
int head_y;
starPosition(star, tail_depth, &tail_x, &tail_y);
starPosition(star, star->depth, &head_x, &head_y);
draw_line(frame, tail_x, tail_y, head_x, head_y,
theme_colours[theme_index][star->colour]);
}
if (last_update_ms - controls_changed_at < WARP_STATUS_MS) {
char text[20];
if (reset_changed) {
snprintf(text, sizeof(text), "A WARP RESET");
} else if (theme_changed) {
snprintf(text, sizeof(text), "C %s", theme_names[theme_index]);
} else {
snprintf(text, sizeof(text), "E SPEED %u", (unsigned)(speed_index + 1U));
}
draw_text_centred(frame, WARP_CENTRE_X, 155, text, 1, COLOR_LIGHTGREY);
}
}Complete original file, including constants and data
/* Coded By JD(2026) */
#error "Reference listing only — not provided as build-ready source."
#include "warp_tunnel.h"
#include "game_graphics.h"
#include "PET2001_font.h"
#include "esp_random.h"
#include <math.h>
#include <stdbool.h>
#include <stdio.h>
#define WARP_STAR_COUNT 72U
#define WARP_THEME_COUNT 4U
#define WARP_THEME_COLOURS 8U
#define WARP_SPEED_COUNT 4U
#define WARP_FRAME_MS 25U
#define WARP_STATUS_MS 1500U
#define WARP_PI 3.14159265f
#define WARP_CENTRE_X (LCD_WIDTH / 2)
#define WARP_CENTRE_Y (LCD_HEIGHT / 2)
#define WARP_RADIUS ((float)LCD_WIDTH * 0.54f)
#define WARP_CENTRE_EMPTY_RADIUS 28.0f
#define WARP_VERTICAL_SCALE 0.54f
typedef struct {
float angle;
float depth;
uint8_t colour;
} warp_star_t;
static const uint16_t theme_colours[WARP_THEME_COUNT][WARP_THEME_COLOURS] = {
{COLOR_DARKGREY, COLOR_GREY, COLOR_LIGHTGREY, COLOR_WHITE,
COLOR_WHITE, COLOR_LIGHTGREY, COLOR_WHITE, COLOR_WHITE},
{COLOR_DARKBLUE, COLOR_BLUE, COLOR_DEEPSKYBLUE, COLOR_CYAN,
COLOR_LIGHTCYAN, COLOR_WHITE, COLOR_CYAN, COLOR_WHITE},
{COLOR_DARKRED, COLOR_FIREBRICK, COLOR_RED, COLOR_ORANGERED,
COLOR_ORANGE, COLOR_YELLOW, COLOR_LIGHTYELLOW, COLOR_WHITE},
{COLOR_RED, COLOR_ORANGE, COLOR_YELLOW, COLOR_LIME,
COLOR_CYAN, COLOR_MEDIUMPURPLE, COLOR_MAGENTA, COLOR_WHITE},
};
static const float speed_multipliers[WARP_SPEED_COUNT] = {
0.55f, 0.85f, 1.25f, 1.75f,
};
static const char *const theme_names[WARP_THEME_COUNT] = {
"WHITE", "CYAN", "FIRE", "RAINBOW",
};
static warp_star_t stars[WARP_STAR_COUNT];
static uint32_t last_update_ms;
static uint32_t controls_changed_at;
static uint8_t speed_index;
static uint8_t theme_index;
static bool reset_changed;
static bool theme_changed;
static bool running;
static void resetStar(warp_star_t *star, bool spread_out)
{
star->angle = (float)(esp_random() % 6284U) * WARP_PI / 3142.0f;
// All stars start beyond the central opening, keeping that area empty.
star->depth = spread_out ? WARP_CENTRE_EMPTY_RADIUS +
(float)(esp_random() % 12000U) / 100.0f :
WARP_CENTRE_EMPTY_RADIUS +
(float)(esp_random() % 1600U) / 100.0f;
star->colour = (uint8_t)(esp_random() % WARP_THEME_COLOURS);
}
static void resetStars(bool spread_out)
{
for (unsigned index = 0U; index < WARP_STAR_COUNT; ++index) {
resetStar(&stars[index], spread_out);
}
}
static void starPosition(const warp_star_t *star, float depth, int *x, int *y)
{
*x = WARP_CENTRE_X + (int)lroundf(cosf(star->angle) * depth);
*y = WARP_CENTRE_Y + (int)lroundf(sinf(star->angle) * depth * WARP_VERTICAL_SCALE);
}
void startWarpTunnel(uint32_t now_ms)
{
resetStars(true);
last_update_ms = now_ms;
controls_changed_at = now_ms;
speed_index = 1U;
theme_index = 0U;
reset_changed = false;
theme_changed = false;
running = true;
}
void stopWarpTunnel(void)
{
running = false;
}
void warpTunnelAction(bool reset, bool next_theme, bool next_speed, uint32_t now_ms)
{
if (!running) return;
if (reset) resetStars(true);
if (next_theme) theme_index = (uint8_t)((theme_index + 1U) % WARP_THEME_COUNT);
if (next_speed) speed_index = (uint8_t)((speed_index + 1U) % WARP_SPEED_COUNT);
if (!reset && !next_theme && !next_speed) return;
reset_changed = reset;
theme_changed = next_theme && !reset;
controls_changed_at = now_ms;
}
void updateWarpTunnel(uint32_t now_ms)
{
if (!running || now_ms - last_update_ms < WARP_FRAME_MS) return;
uint32_t elapsed_ms = now_ms - last_update_ms;
if (elapsed_ms > 50U) elapsed_ms = 50U;
last_update_ms = now_ms;
const float elapsed = (float)elapsed_ms / 1000.0f * speed_multipliers[speed_index];
for (unsigned index = 0U; index < WARP_STAR_COUNT; ++index) {
warp_star_t *star = &stars[index];
star->depth += (35.0f + star->depth * 1.15f) * elapsed;
if (star->depth > WARP_RADIUS) resetStar(star, false);
}
}
void drawWarpTunnel(uint16_t *frame)
{
if (!running || frame == NULL) return;
clear(frame, COLOR_BLACK);
for (unsigned index = 0U; index < WARP_STAR_COUNT; ++index) {
const warp_star_t *star = &stars[index];
if (star->depth <= WARP_CENTRE_EMPTY_RADIUS) continue;
// Clip the streak at the opening rather than allowing its tail into it.
const float tail_depth = fmaxf(star->depth * 0.76f, WARP_CENTRE_EMPTY_RADIUS);
int tail_x;
int tail_y;
int head_x;
int head_y;
starPosition(star, tail_depth, &tail_x, &tail_y);
starPosition(star, star->depth, &head_x, &head_y);
draw_line(frame, tail_x, tail_y, head_x, head_y,
theme_colours[theme_index][star->colour]);
}
if (last_update_ms - controls_changed_at < WARP_STATUS_MS) {
char text[20];
if (reset_changed) {
snprintf(text, sizeof(text), "A WARP RESET");
} else if (theme_changed) {
snprintf(text, sizeof(text), "C %s", theme_names[theme_index]);
} else {
snprintf(text, sizeof(text), "E SPEED %u", (unsigned)(speed_index + 1U));
}
drawPet2001TextCentredTransparent(frame, WARP_CENTRE_X, 155, text,
COLOR_LIGHTGREY, 1);
}
}