Skip to content

About

A 3D raycasting maze game rendered entirely in your terminal.

Topics

Resources

Stars

11 stars

Watchers

0 watching

Forks

Repository files navigation

term-maze-raycast

Go 版 raycast 风格 3D 迷宫:融合

  • raycast-game — 画面与操作:墙壁 / 天花板 / 地板 / 俯仰 / 视高 / 视野的 DDA 光线投射渲染,按键布局完全一致
  • term-maze-3d — 迷宫玩法:随机迷宫、自由探索

Go 实现,零第三方图像库,仅依赖 eiannone/keyboard(按键)与 x/sys/unix(终端尺寸)。同一份源码提供两套构建:

构建 目标 音频 画面节拍 生成并行 视频解码
默认(Linux) 桌面 Linux 优先 ffplay 60fps 最多 16 核 ffmpeg,优先 -hwaccel auto 显卡硬解
-tags termux Termux(Android) 优先 termux-media-player 40fps 最多 4 核 ffmpeg 软解

两者都只要求 ffmpeg(仅 mp4 需要),图片/GIF 用 Go 标准库。

画面

  • 墙壁使用 DDA 光线投射 + 边缘描边:竖直边 |、水平边 _(俯仰时 / \)、转角 ·
  • 天花板留空,地板用 . 填充,地平线随俯仰 / 视高偏移
  • 画面自适应终端尺寸:终端缩小或放大,游戏画面跟着缩放,不会出现乱码

迷宫

  • 巨型随机迷宫,默认 1000×1000,递归回溯生成,所有通路互相连通,绝不封死道路、没有孤岛
  • 生成后再随机拆墙(braiding)打通大量回环,随便逛都不会被堵住
  • 无出口、无胜利画面,纯自由探索;玩家出生点固定在迷宫左上角

性能

  • 生成提速:一次开传奇数格棋盘空间,命中率恒定,大尺寸迷宫数百毫秒内完成
  • 渲染提速:列缓冲 / 行缓冲 / 帧缓冲跨帧复用,零每帧分配;光线给 512 步上限防长走廊卡顿
  • 生成提速:彩蛋墙改为 1024 张图案池(图案由种子派生、随种子可重现),1501² 大图不再为每格存一张 8×8 图案,生成内存从约 25MB 降到不足 1MB;600² 以上按核数并行挖通道,小图自动串行
  • 帧率:Linux 版 60fps、Termux 版 40fps;画面增量重绘,只在内容变化时才发送该行,画面静止时一字节都不写(状态行只保留开机按键提示与「小地图开/关」「视野」等瞬时信息,不显示 FPS/坐标)
  • 硬件利用:画面由终端自身(GPU 加速的文本渲染)绘制,游戏只喂字节流;Linux 版额外让 ffmpeg 用 -hwaccel auto 走显卡解码视频,失败自动回退软解
  • 画面稳定:终端尺寸每 100ms 采样一次并保持稳定,弹出软键盘/瞬时抖动不会导致画面来回跳动;尺寸真正变化时清屏一次,不乱码
  • 按键:1 右转、3 左转
  • 移动/转向即时响应:每按一次键立刻走一步(按住可连续移动),松开后做 250ms 的平滑滑动衔接,不依赖终端按键自动重复,Linux 桌面终端上也顺滑
  • 开局通道固定打通:出生点北、东两侧始终有三条可行走路径,不会开局顶着墙
  • 退出(q 或 Ctrl-C)会完整恢复终端回显与行模式,退出后照常输入
  • 小地图为玩家周围区域的局部视图(占用屏幕左上的 1/4),成本与迷宫大小无关

操作(与 raycast-game 一致)

按键 功能
2 / 8 前进 / 后退
4 / 6 向左 / 向右平移
1 / 3 向左 / 向右旋转
5 / 0 摄像头往上 / 往下
7 / 9 抬头 / 低头
+ / - 增加 / 减少视野
% 开关小地图(左上角占屏幕 1/4)
/ 进入底部命令终端(见下)
q 退出

命令终端 /

按 / 进入底部悬浮的命令行(收起时约占屏幕 1/3):输入命令、回车执行,↑/↓ 翻命令历史,输出区用 PgUp/PgDn 或 Ctrl+U/Ctrl+D 滚动(底部状态行会显示可见范围),ESC 返回游戏。动画期间不节流、缓动滑入/滑出,收放平滑。同样支持管道与逻辑连接:|(管道)、&&/||、;、单/双引号与反斜杠转义,结构如 sh。命令只对本游戏内置命令生效,外部命令一律拒绝并提示未知命令(用 help 查看全部可用命令)。

命令 功能
help 显示全部命令帮助
clear 清空命令历史
where 位置 / 楼层 / 朝向 / 俯仰 / 高度 / 视野
home 回出生点
tp x y 传送到指定坐标(墙与越界会拒绝)
seed 显示当前地图种子
fov [值|wide|normal|+|-] 视野 0.5~5,默认 1
height [值|high|low|ground|+|-] 视高 -5~5,默认 0
reset 重置俯仰与视高
spin [on|off] 视角自动旋转(游戏内任意键停止)
flip 上下翻转视角
party 轮换墙体 ASCII 样式
floorinfo 当前楼层信息
space|space close 200×200 平地模式 / 返回迷宫
door [x y|open|close [all]|list] 放门 / 开合 / 列出(小地图 D,关门挡路)
bookmark [名] 标记当前位置
goto [名] 传送到书签(跨楼层会重建该楼层)
elevator [楼层|home|list] 电梯换层,种子固定可重现
edit / edit off 进入/退出编辑模式(Q 退出)
img load <文件> [x y] 贴图片到墙面:.png/.jpg/.gif 自动转彩色 ASCII(真彩背景),其余当文本画;缺省自动找玩家附近的墙放置
img list / remove list 同时列出 ~/ 下的图片文件与已贴图 / 卸载贴图
video play <文件> [x y] 墙面播放:.mp4 用 ffmpeg 抽帧转 ASCII 真彩 10fps 且带音轨(音频优先 ffplay,其次 termux-media-player;只有 ffmpeg 一个必需外部工具,且仅 mp4 需要);.gif/.png/.jpg 纯 Go 标准库解码;文本格式帧之间用 --- 行分隔。可同时播放多个视频
video stop [id] 停止播放(省略 id 停止全部,含音轨)
video remove <id|all> / img remove <id|all> 删除贴墙视频/图片
video list 查看正在播放的视频(同时列出 ~/ 下的 gif/mp4)
save [名] 存为 ~/名.rmap(RAMAP,含楼层/玩家/门/地图)
load [名] 载入 ~/名.rmap
file <路径> 识别文件:本游戏存档 / ELF / 未知

编辑模式按键:2/8/4/6 或方向键移动光标、0空地 1墙 空格切换、D放门、G抓取、P放置、Q退出。where | seed 等内置命令可参与管道;save smoke && file smoke.rmap 同级联执行。存档只写入 ~ 目录,不执行任何外部命令。

游戏内按 空格 跳跃(抛物线带重力,跳跃中不可再起跳)。地图生成时约 9% 的墙会随机变成彩蛋墙:每面墙随机从十余种形状族(实心/环形菱形、圆、方框、十字、沙漏、四角、X 斜带等)抽取一个严格左右+上下对称的 8×8 像素画,用 ASCII 特殊字符(& ; ~ % / = $ ^ ! * ?)直接画在墙面上;每次重建地图(reset/elevator)图案都会重新随机,且随迷宫种子可重现。彩蛋墙不阻挡任何操作,小地图显示 %。贴图与视频以 ASCII 直接呈现在墙面上(真实图片/视频按亮度降采样成 .·:;!%#@ 字符画,每格一真彩背景色,配 256 色/真彩终端即可看到彩色画面),凡是贴了图或视频的墙,小地图统一从 # 变为 I。

构建运行

依赖:Go 1.22+;ffmpeg 仅 mp4 贴图/视频需要。Linux 用 apt install golang ffmpeg(Fedora dnf、Arch pacman),Termux 用 pkg install golang ffmpeg。

cd term-maze-raycast

# Linux 版(产物命名:平台-名称-版本)
GOOS=linux CGO_ENABLED=0 go build -o linux-$(go env GOARCH)-term-maze-raycast-1.0.0 .

# Termux 版(Android/arm64;在 Termux 里可省略 GOOS/GOARCH)
GOOS=android GOARCH=arm64 CGO_ENABLED=0 go build -tags termux -o termux-arm64-term-maze-raycast-1.0.0 .

BIN=./linux-amd64-term-maze-raycast-1.0.0   # Termux 版换成 termux-arm64-...
$BIN                  # 默认 1000×1000
$BIN 600              # 生成 601×601(自动归一为奇数)
$BIN 2000             # 更大尺寸
$BIN -s world         # 启动即读 ~/world.rmap
$BIN --save=~/a.rmap  # 也可用 --save / --save= / -s= / -s路径

小地图中:四周用 | 围边、# 墙壁、P 玩家、空格空地(显示玩家周围区域,占屏幕左上的 1/4)。

About

A 3D raycasting maze game rendered entirely in your terminal.

Topics

Resources

Stars

11 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages