智能大屏系统
这是一个基于 ComputerCraft 的智能大屏系统,包含服务端和客户端两部分。
- 服务端负责屏幕矩阵配置、媒体库管理、磁盘发盘、播放列表调度和红网通信。
- 客户端负责触控 UI、屏幕绑定、媒体导入、系统参数配置和播放控制。
- 媒体文件以
.32vid格式存放在磁盘中,并配套一个.json元数据文件。
目录结构
startup.lua:服务端主程序。Client.lua:客户端主程序模板。monitor_server_config.json:服务端持久化配置。32vid-player-mini.lua:媒体播放脚本。basalt.lua:Basalt UI 库。utf8display.lua:UTF-8 文本转位图工具。ime_lib.lua:输入法交互库。json.lua:JSON 编解码库。
依赖仓库来源:
ime_lib.lua:https://git.liulikeji.cn/xingluo/cc_rimebasalt.lua:https://git.liulikeji.cn/GitHub/Basalt2utf8display.lua:https://git.liulikeji.cn/xingluo/ComputerCraft-Utf8/src/branch/main/utf8displayjson.lua:https://git.liulikeji.cn/GitHub/json.lua
系统架构
服务端
服务端程序为 startup.lua,负责以下工作:
- 打开 modem 并通过
rednet与客户端通信。 - 维护屏幕矩阵、单屏块大小、屏幕绑定关系。
- 管理写盘驱动器和媒体库索引。
- 将客户端程序和依赖库写入目标磁盘。
- 提供媒体导入、删除、重命名、播放列表保存等请求处理。
- 定时刷新媒体展示和播放列表状态。
当前服务端事件循环已经拆成多个并行 worker,分别处理:
rednet_messagemonitor_touchdiskdisk_eject- 媒体刷新轮询
- 播放列表轮询
客户端
客户端程序为 Client.lua,通过 Basalt 构建触屏 UI,主要页面包括:
- Home:媒体库浏览、媒体信息、导入入口。
- Settings:屏幕设置、写盘驱动设置、磁盘列表、系统参数。
- Playlist:播放列表编辑、启停、媒体项和睡眠项维护。
客户端和服务端通过两个 rednet 协议通信:
- 客户端发送协议:
monitor_matrix_client_to_server - 服务端发送协议:
monitor_matrix_server_to_client
实际发盘后的客户端启动文件会把这两个协议替换成服务端当前生成的随机 key,避免多套系统互相串线。
运行机制
服务端启动
运行 startup.lua 后,服务端会:
- 自动检查并下载缺失依赖。
- 加载
monitor_server_config.json。 - 检测当前可用屏幕和磁盘驱动器。
- 如果未设置
write_drive_name,要求你在终端手动选择一个写盘驱动。 - 启动 rednet 服务、媒体索引扫描、播放列表轮询和屏幕刷新。
客户端自动切换服务端模式
Client.lua 顶部带有一个特殊逻辑:
- 如果当前机器本地存在
monitor_server_config.json - 且其中配置的
write_drive_name对应的是一个本机可用的 drive
那么客户端会直接执行 /startup.lua,转为服务端运行。
这意味着:
- 放在服务端电脑里的这套程序,默认会进入服务端模式。
- 通过发盘写入磁盘的客户端副本,不带服务端配置文件时,会正常进入 UI 客户端模式。
- 作用是为了让客户端始终插入基座时包含服务端不受其启动文件影响(避免启动为客户端)
首次部署
1. 准备硬件
至少需要以下外设:
- 1 台 ComputerCraft 电脑作为服务端
- 1 个 modem
- 多块 monitor
- 至少 2 个 drive
- 一个带modem的手提电脑
- 至少 1 张磁盘/任意有id电脑用媒体存储
远程转码和输入法功能需要:
-
可访问的媒体转码接口: 服务端:xingluo/GMapiServer: 提供api接口的服务端 - GMapiServer - 花璃科技代码站 默API:http://newgmapi.liulikeji.cn/api/sanjuuni/async
-
可访问的 IME 查询接口: 服务端:xingluo/cc_rime: 用于cc:t的中文输入法 - cc_rime - 花璃科技代码站
2. 放置程序文件
wget https://git.liulikeji.cn/xingluo/cc-t-display-wall/raw/branch/main/startup.lua
3. 启动服务端
运行:
startup
首次启动如果没有 write_drive_name,终端会提示选择写盘驱动器。
此驱动器用于客户端基座和配置写入
4. 发盘给客户端机器
服务端会把以下文件写入选中的写盘:
startup.lua,内容是带协议头的客户端启动文件basalt.luautf8display.luaime_lib.luajson.lua
把客户端电脑插入后等一秒然后拿出后启动,即可进入触摸 UI。
屏幕配置
屏幕矩阵
屏幕设置页中包含两组核心参数:
- Matrix Size:整个大屏由多少块显示器组成,例如
4 x 3 - Block Size:单块显示器的逻辑块尺寸,例如
8 x 6
预览与保存
- 点
Set会刷新本地预览。 - 点
Save会把当前预览矩阵、块大小和绑定关系保存到服务端配置。 - 只有本地待保存值与服务端当前值不一致时,保存按钮才会出现。
引导绑定
支持引导式屏幕绑定:
- 先设置矩阵大小。
- 点击
Guide。 - 服务端会在所有 monitor 上显示当前待绑定位置。
- 依次触摸实际屏幕完成绑定。
- 绑定完成后点击保存。
媒体系统
媒体文件结构
每个媒体会以两份文件存放在目标磁盘上:
<file_id>.32vid:实际视频文件<file_id>.json:元数据文件
元数据包含:
idnamesizeurlresolutioncharacter_sizeblock_size
导入流程
客户端导入媒体的当前流程为:
- 输入源地址。
- 由远程转码接口生成
.32vid下载地址。 - 客户端请求服务端执行
prepare_media_file。 - 服务端先把转码结果下载到内存缓存。
- 客户端根据真实
file_size选择足够大的目标磁盘。 - 通过 IME 输入媒体名称。
- 客户端请求
save_media_file,服务端将缓存写入磁盘。
媒体库管理
当前支持:
- 浏览媒体库
- 查看媒体信息
- 重命名媒体
- 删除媒体
- 请求播放指定媒体
媒体重命名只会更新 .json 中的 name,媒体 id 保持不变。
播放列表
播放列表支持两类项目:
media:播放指定媒体sleep:等待指定秒数
当前持久化格式中,媒体项只保存:
{ "type": "media", "file_id": "xxxxxxx" }
系统参数
系统参数页当前可配置:
web_api_url:远程转码接口地址extra_convert_args:附加转码参数ime_api_url:IME 查询接口地址
这些值保存在 monitor_server_config.json 的 system 字段中。
默认值来源:
- 转码接口:
http://newgmapi.liulikeji.cn/api/sanjuuni/async - IME 接口:
https://rime.liulikeji.cn/query - 额外参数:
-k
配置文件说明
服务端配置文件为 monitor_server_config.json。
主要字段包括:
matrixassignmentsblock_sizewrite_drive_namecurrent_media_idplaylistsystemclient_send_keyclient_receive_key
示例结构:
{
"matrix": { "width": 4, "height": 3 },
"block_size": { "width": 8, "height": 6 },
"assignments": {
"1_1": "monitor_37"
},
"write_drive_name": "left",
"current_media_id": "wwr2xtin",
"playlist": {
"enabled": false,
"current_index": 1,
"items": [
{ "type": "media", "file_id": "36vzb4or" },
{ "type": "sleep", "seconds": 3 }
]
},
"system": {
"web_api_url": "http://newgmapi.liulikeji.cn/api/sanjuuni/async",
"extra_convert_args": "-k",
"ime_api_url": "https://rime.liulikeji.cn/query"
}
}
主要请求类型
客户端当前会向服务端发送以下主要请求:
get_stateget_monitor_character_infomonitor_preview_pingsave_statesave_assignmentstart_guided_bindingstop_guided_bindingcommit_guided_bindingset_write_drivesave_system_configprepare_media_filesave_media_filerename_media_filedelete_media_filesave_playlist