Compare commits

..

292 Commits

Author SHA1 Message Date
MrZ626
b44d144b26 特别感谢添加一位
赞助添加一位
2021-08-11 01:38:10 +08:00
MrZ626
376a528fac 选择语言时会先清除上一个文本然后再生成新的 close #189 2021-08-10 23:47:00 +08:00
MrZ626
6dec156d4d 修改日志和build号 2021-08-10 20:27:07 +08:00
MrZ626
372f27b6ac 提升puzzleMark材质透明度
略微提升自定义-拼图性能
2021-08-10 20:09:47 +08:00
MrZ626
d6d2d394bc 修改玩家绘制流程,修复镜头平移和遮罩的一些冲突 2021-08-10 19:54:51 +08:00
MrZ626
7c326ce0d7 修复联网游戏房间内菜单按钮位置不正确 2021-08-10 17:59:52 +08:00
MrZ626
1ae26d39c2 再次修复进入游戏场景时初始化代码顺序错误 2021-08-10 16:13:36 +08:00
scdhh
702d427183 修正Android的CI问题 (#185)
* 删除不需要的re模块

* 添加编译过程中向源码添加提交hash的步骤

* 修正变量

* 整理代码

* 修正Android的CI问题
2021-08-10 15:41:20 +08:00
MrZ626
432ba338b7 添加issue模板 close #187 2021-08-10 15:37:40 +08:00
scdhh
c1ce09ac52 在自动打包的时候添加提交hash #176 (#184)
* 删除不需要的re模块

* 添加编译过程中向源码添加提交hash的步骤

* 修正变量

* 整理代码
2021-08-10 03:38:59 +08:00
MrZ626
57982d3c43 修改更新历史 2021-08-10 03:34:41 +08:00
MrZ626
c168a6c685 整理代码 2021-08-10 03:33:25 +08:00
MrZ626
17479ac08b 玩家绘制模块改动,applyFieldOffset函数改为applyField,组合更多功能
修复部分模式往场地内部绘制信息时偏移问题
close #181
2021-08-10 03:32:07 +08:00
MrZ626
a73819214b 修改更新历史和build号 2021-08-10 02:51:33 +08:00
MrZ626
c5730b31f7 tsd困难在同一列只允许连续做最多三个T2,微调参数 2021-08-10 02:50:51 +08:00
MrZ626
4bfebdea13 整理旋转相关代码,希望能进一步解决神秘的旋转时报错问题 2021-08-10 02:02:47 +08:00
MrZ626
d040754d8c 取消暂停过程中允许再次暂停 2021-08-10 01:09:34 +08:00
MrZ626
7943ebc8f8 略微减轻lightning2背景瞎眼程度 2021-08-10 00:01:14 +08:00
MrZ626
5ce0b90d9f 所有踢墙表数据和旋转中心位置数据完全独立,希望能解决神秘的旋转时报错问题,需要再研究 2021-08-09 23:56:19 +08:00
MrZ626
e97d892926 降低隐形n/h/l的S和A评级标准 2021-08-09 22:57:37 +08:00
MrZ626
3b026ce204 降低无尽pc的S线至50,同时加快速度提升 2021-08-09 22:48:08 +08:00
MrZ626
d269828924 删除一个已经合并到TABLE模块的无用文件 2021-08-09 22:34:42 +08:00
MrZ626
1e1560651a 修复debug模式下f4可能引起报错 close #183 2021-08-09 22:34:16 +08:00
MrZ_26
782e1ef506 Merge pull request #180 from Trebor-Huang/main
修正Android与OS X的CI问题
2021-08-09 19:55:02 +08:00
Trebor-Huang
3a3c805792 修正Android与OS X的CI问题 2021-08-09 14:22:37 +08:00
Trebor-Huang
51235a61ad Merge branch '26F-Studio-main' 2021-08-09 14:16:00 +08:00
Trebor-Huang
f493de998c Merge branch 'main' of https://github.com/26F-Studio/Techmino into 26F-Studio-main 2021-08-09 14:15:33 +08:00
MrZ626
72b5acfece 修正旋转系统设置重置条件 2021-08-09 14:02:43 +08:00
MrZ626
176ddf6abb 完善xiaoya语音包 2021-08-09 12:45:41 +08:00
MrZ626
44c52300e4 更新世界纪录 2021-08-09 12:36:12 +08:00
MrZ626
2eae6cdfda 修复计算器的一些问题 close #178 close #179 2021-08-09 11:53:56 +08:00
MrZ_26
0f896d0a4f Merge pull request #177 from shoucandanghehe/main
实时更新的actions产物文件名
2021-08-09 11:37:18 +08:00
MrZ626
02189c4262 可以修改O块初始方向 2021-08-09 11:35:04 +08:00
d649a0caa1 统一代码风格 2021-08-09 08:21:31 +08:00
e28894549c C M D 害 人 2021-08-09 08:16:11 +08:00
b3ef90237f 又换回了bat尝试解决无法添加变量的问题 2021-08-09 07:52:42 +08:00
ebc4e08986 尝试使用python解决bat无法添加变量的问题 2021-08-09 07:39:26 +08:00
8d74a35f29 添加version至环境变量 2021-08-09 07:17:19 +08:00
a37e164c0b 修正python脚本路径 2021-08-09 07:12:43 +08:00
a71b504589 修改actions上传名称,修改编译时依赖的python脚本 2021-08-09 07:10:40 +08:00
MrZ626
20cd27d7f6 再微调大量模式的左侧信息显示
stack模式左侧信息添加"块数"标签
2021-08-09 03:16:40 +08:00
MrZ626
ac889dcba9 修复进入游戏场景时初始化代码顺序错误 2021-08-09 02:33:05 +08:00
MrZ626
70bbb12285 调整游戏底部常驻版本号,移除short项 2021-08-09 02:23:39 +08:00
MrZ626
e7e568f67a 微调几乎所有模式左侧信息位置,对齐hold框中间 2021-08-09 02:22:15 +08:00
MrZ626
3452ae1d66 修改更新历史和版本号 2021-08-09 01:40:00 +08:00
MrZ626
2ad336b13a 添加游戏中菜单按钮位置设定 2021-08-09 01:39:18 +08:00
MrZ626
78b15b78fa 每个旋转系统有自己独特的旋转中心样式
整理代码
2021-08-09 01:15:04 +08:00
MrZ626
eb7b637703 添加Classic和Classic_plus旋转系统 close #173 2021-08-09 00:13:57 +08:00
MrZ626
b083a0801f 旋转系统模块重构,支持无旋转中心 close #168 2021-08-08 23:51:46 +08:00
MrZ626
471f1076c4 TABLE.shift新增depth参数 2021-08-08 23:51:46 +08:00
MrZ626
e50fe63e02 TABLE.copy新增depth参数 2021-08-08 23:51:45 +08:00
MrZ626
7682054dea 微调lNavy颜色 2021-08-08 23:51:45 +08:00
MrZ626
1e3c2f039b 修复暂停界面雷达图线框显示问题 2021-08-08 23:51:45 +08:00
MrZ626
a832e56b42 统一四连块英文名为Tetromino 2021-08-08 15:54:21 +08:00
MrZ626
3858cfd9ba 整理代码 2021-08-08 15:04:44 +08:00
MrZ626
5b4fd892ff 修正kpm计算一处多余的+1,优化更新格子可见性代码 2021-08-08 03:36:16 +08:00
MrZ626
4ffa88805c 再调整暂停ui 2021-08-08 03:08:51 +08:00
MrZ626
2a0b26f2fd GC拓展模块调整,圆角正多边形成为绘图函数 2021-08-08 03:08:35 +08:00
MrZ626
30308eb308 调整两个彩色logo的颜色量 2021-08-08 00:02:25 +08:00
MrZ626
5f8cbe524e 圆角圆角圆角圆角圆角 2021-08-08 00:02:07 +08:00
MrZ626
a2f0142712 调整全局颜色表,降低饱和度 2021-08-07 23:37:50 +08:00
MrZ626
d2c6529d2a 修复计算器的一些小bug 2021-08-07 22:05:02 +08:00
MrZ626
b23e32df7f 修改更新历史和build号 2021-08-07 20:24:37 +08:00
MrZ626
a94a0a2f87 修改几个旋转系统的名字,更新时自动重置旋转系统设置 2021-08-07 20:20:07 +08:00
MrZ626
6fe40e9438 高速经典场地高度改为19 close #169 2021-08-07 20:12:01 +08:00
MrZ626
d4523e8e1d 添加隐藏模式marathon_bfmax的入口并修改tip关于隐藏模式的说法 2021-08-07 20:02:43 +08:00
MrZ626
9fadef2a6e 修复皮肤设置界面旋转方块几圈后重进会看到旋转动画 2021-08-07 20:00:51 +08:00
MrZ626
1970a1b47d 改正一处拼写错误,简化the_box谜题 2021-08-07 19:51:06 +08:00
MrZ626
19d090859c 减暗暂停的背景色,取消暂停的动画改成条形计时器 2021-08-07 19:51:02 +08:00
MrZ626
7fda77bd1e 自定义游戏里重设全部的同时也会清空数据文件 2021-08-07 19:39:31 +08:00
MrZ626
34c14c922c 再调整暂停界面ui,mod和暂停统计不重叠,开始游戏前整个右侧信息框和相关按钮都不出现 2021-08-07 17:40:11 +08:00
MrZ626
0f8a1057dc 所有mod的颜色换成浅色 2021-08-07 17:09:08 +08:00
MrZ626
a74faca9cb 大改暂停界面ui 2021-08-07 17:09:01 +08:00
MrZ626
336aa85cf8 key控件新增fShade属性(自定义亮起素材) 2021-08-07 16:56:08 +08:00
MrZ626
43710a4c4d GC.DO添加fRPol命令 2021-08-07 16:55:15 +08:00
MrZ626
451cf90939 整理代码 2021-08-07 15:42:00 +08:00
MrZ626
6713f48361 优化控制台sudo命令的交互 close #171 2021-08-07 15:27:38 +08:00
MrZ626
f6e3b35482 DOGC移入GC拓展模块,GC.DO添加dRPol(圆角正多边形)命令 2021-08-07 14:55:19 +08:00
MrZ626
1d7e58d3bf 移除联网对战bgm列表里的warped 2021-08-07 01:15:51 +08:00
MrZ626
b501cd374b 整理代码,调整大量场景内绘图用的纯白色和纯黑色 2021-08-06 19:16:01 +08:00
MrZ626
e6f5723ecc 整理代码,混战模式信息显示函数移入玩家模块统一调用 2021-08-06 17:43:43 +08:00
MrZ626
998c79d331 进度显示器移入常用玩家draw函数并微调 2021-08-06 09:58:26 +08:00
MrZ626
a21d6e834d 整理代码,从Player:drop中抽离出几个过程 2021-08-06 01:49:28 +08:00
MrZ626
a4541dd764 重开按钮改成图标,微调模式文字位置 2021-08-06 01:07:05 +08:00
MrZ626
e788dd543e 再调整暂停界面ui 2021-08-06 00:47:53 +08:00
MrZ626
f24fa81d87 微调staff表,修改更新历史和build号 2021-08-06 00:26:49 +08:00
MrZ626
20fb2a3e92 大改暂停界面ui 2021-08-06 00:22:35 +08:00
MrZ626
e7f77291e4 修游戏中ui小问题 2021-08-06 00:22:19 +08:00
MrZ626
fa0848c8b2 调整录像回放时逐帧按钮图标,修复按空格按钮状态未切换 2021-08-06 00:14:43 +08:00
MrZ626
8a740091b3 修复ARS的180有踢墙 2021-08-05 22:15:03 +08:00
MrZ626
5fa3be5886 缩小三格高的方块在next/hold里的显示尺寸 2021-08-05 22:08:11 +08:00
MrZ626
a9d2f097d8 调整游戏内ui和控件ui:
默认背景色调整
减少纯白色使用
减小线宽
增加圆角
2021-08-05 17:58:09 +08:00
MrZ626
450483acc7 关闭背景的默认颜色修改 2021-08-05 15:43:19 +08:00
MrZ626
43019185a8 TRS的R/Y块踢墙表添加一项 2021-08-05 15:42:53 +08:00
MrZ626
f537b36662 修改词典中ppt词条说法 2021-08-05 15:42:26 +08:00
MrZ626
98385b8b56 改对readme里官网链接 2021-08-05 14:45:31 +08:00
MrZ626
8d44046a90 修复asc踢墙表第一项不是00和按180度旋转会爆炸 2021-08-05 14:27:05 +08:00
MrZ626
9b1ab459a0 添加两个赞助者
修改更新历史
2021-08-05 13:42:50 +08:00
MrZ626
f4c0d19734 房间版本不一致时显示的文本会根据设置语言变化 2021-08-04 21:24:43 +08:00
MrZ626
f088bdcf8b 修复松开鼠标可能不触发场景内事件 2021-08-04 20:15:15 +08:00
Trebor Huang
60600dbe2f 修正OS X CI错误 (#166)
* 增加OS X签名

等证书搞好之后改一下里面的id之类的就行。

* 添加证书信息

* 修正OS X CI错误
2021-08-04 20:11:07 +08:00
Trebor-Huang
eb95cc4b47 修正OS X CI错误 2021-08-04 19:57:51 +08:00
Trebor Huang
57dfdacffa Merge branch '26F-Studio:main' into main 2021-08-04 19:53:03 +08:00
scdhh
0c839790fe 修正actions使用的macos版本 2021-08-04 19:47:18 +08:00
scdhh
1f29916e09 修正actions使用的macos版本 2021-08-04 19:45:16 +08:00
MrZ626
310023dc94 修复长按hold成功后会触发IHS close #165 2021-08-04 18:33:39 +08:00
Trebor Huang
9448dcefb4 增加OS X签名 (#161)
* 增加OS X签名

等证书搞好之后改一下里面的id之类的就行。

* 添加证书信息
2021-08-04 18:33:06 +08:00
MrZ626
167e77ddf2 修正ws模块连接成功后没有把timeout设为0 2021-08-04 00:31:31 +08:00
MrZ626
dc586ad82e 修复回放录像时显示的玩家名不正确 2021-08-04 00:27:52 +08:00
MrZ626
6d331f882f 修改更新历史和build号 2021-08-03 23:59:20 +08:00
MrZ626
b945760c72 再调整堆积模式参数 2021-08-03 23:57:59 +08:00
MrZ626
98aa49c2c3 导入录像时会先检测重复文件名 2021-08-03 23:50:46 +08:00
MrZ626
78feab88bf 文件模块save方法新增d参数 2021-08-03 23:50:33 +08:00
MrZ626
6f005d467d 微调语言文件一两条 2021-08-03 23:50:01 +08:00
MrZ626
324011f01b 回放列表添加导出到剪切板/从剪切板导入的按钮 2021-08-03 23:13:01 +08:00
Trebor-Huang
0d97d2a02d 添加证书信息 2021-08-03 22:23:40 +08:00
MrZ626
37bec38524 添加几个中文tip 2021-08-03 20:59:10 +08:00
MrZ626
847795c0ef 调整堆积模式规则 2021-08-03 20:52:00 +08:00
Trebor-Huang
aa1a5a1550 增加OS X签名
等证书搞好之后改一下里面的id之类的就行。
2021-08-03 17:48:37 +08:00
MrZ626
997b3cbecd 整理代码,添加回放文件格式说明 2021-08-03 16:31:19 +08:00
MrZ626
652aced790 点击进入房间后一段时间不能进行其他操作 2021-08-03 16:30:27 +08:00
MrZ626
47af067c03 修复房间列表输密码的时候部分按键还会有其他功能 2021-08-03 15:48:35 +08:00
MrZ626
5b31e3eb87 调整确认删除的提醒问号时间计算方法和位置 2021-08-03 15:35:51 +08:00
MrZ626
0bb4b069e7 更换堆积40/100模式的序列 2021-08-03 15:22:53 +08:00
MrZ626
eded658d38 修正序列设置有错误时弹出信息有误 2021-08-03 15:22:37 +08:00
MrZ626
1caeb0ed6b 修改更新历史 2021-08-03 03:18:37 +08:00
MrZ626
611a1f0a04 更换挖掘和生存-3/4模式的bgm 2021-08-03 03:18:35 +08:00
MrZ626
13e58e6f80 新增三个堆叠模式 close #142 2021-08-03 03:11:21 +08:00
MrZ626
d6853d381f 修正tsd_u模式的标志光柱位置小bug 2021-08-03 02:38:26 +08:00
MrZ626
b6cc14fe2f 更新模式文件说明文档
修改更新历史
2021-08-03 02:09:15 +08:00
MrZ626
9b1f9fa9dd 整理模式代码:
移除无用的pauseLimit
移除重复的模式load函数(自动创建一个玩家)
2021-08-03 02:05:13 +08:00
MrZ626
cca53b6376 第一次启动会自动进入语言设置菜单 close #150 2021-08-03 01:57:18 +08:00
MrZ626
1aa991f89f 静音按钮再次点击可以重新开启声音了 2021-08-03 01:27:13 +08:00
MrZ626
7407bbefdf tsd_u中结束游戏的重复T2不计入成绩 2021-08-03 00:37:49 +08:00
MrZ626
40fb835d9c 大量调整中文tip 2021-08-03 00:34:14 +08:00
MrZ626
e4df92fb54 更新世界纪录
语音staff添加Xiaoya
2021-08-03 00:10:22 +08:00
MrZ626
7b9760e376 修正加载小问题 2021-08-02 23:47:54 +08:00
MrZ626
52607545fa 修改更新历史和build号 2021-08-02 23:34:33 +08:00
MrZ626
849756531d 从暂停界面回到游戏界面不改变回放速度 2021-08-02 23:34:32 +08:00
MrZ626
2e16240fb8 新增tsd极限模式(填坑) close #157 2021-08-02 23:34:32 +08:00
MrZ626
181beda455 提升tsd困难的难度,调整评分标准 2021-08-02 23:34:32 +08:00
MrZ626
d0f77f4b78 lastPiece新增放置的方块位置、中心位置和朝向信息 2021-08-02 23:34:32 +08:00
MrZ626
dea2f6c8d7 修复录像回放速度和按钮状态刷新问题 close #159 close #160 2021-08-02 22:09:50 +08:00
MrZ626
615fd414ec 恢复刷新在线玩家人数并且降低请求频率 2021-08-02 21:12:01 +08:00
MrZ626
7296498410 调整几个中文tip 2021-08-02 21:05:11 +08:00
MrZ626
554970c036 修复wing背景水晶尺寸没有跟随屏幕尺寸调整,微调水晶颜色 2021-08-02 21:01:28 +08:00
MrZ626
057abe6ba5 整理代码,加载设置和统计的代码移至main.lua 2021-08-02 16:58:21 +08:00
MrZ626
3b215eb7af TABLE扩展模块新增一个函数 2021-08-02 16:58:21 +08:00
MrZ626
1abaa0e5c5 添加一个赞助者 2021-08-02 16:53:16 +08:00
MrZ626
0c5cb1686e 更新特别感谢名单 2021-08-02 15:00:00 +08:00
MrZ626
21f0aabae0 取消加载完成时的emit音效 2021-08-02 03:30:10 +08:00
MrZ626
e5458c1ab9 升级STRING.readLine功能 2021-08-02 03:13:51 +08:00
MrZ626
a30c0395aa 对战房间背景和音乐不再能自定义,都改为列表随机 2021-08-01 19:47:59 +08:00
MrZ626
0b9006faf3 修复读取到本地没有的旋转系统会直接蓝屏
升级房间版本号
整理代码
2021-08-01 19:47:59 +08:00
MrZ626
adefb776fe 修复加载自定义模式参数文件时可能报错 2021-08-01 19:47:59 +08:00
MrZ626
ee089b0f31 master_ph模式更换背景 close #158 2021-08-01 19:47:58 +08:00
flaribbit
44200458c5 Merge pull request #156 from Trebor-Huang/main
add CI for macOS
2021-08-01 11:35:00 +08:00
flaribbit
5d2d4eae17 Update build.yml
add download link, remove blank lines
2021-08-01 11:33:44 +08:00
Trebor Huang
25f87cae53 [no ci] CI for OS X
依赖于一个还没上传的模板,还没决定这个要放在哪,所以链接留空。
2021-08-01 03:05:48 +08:00
Trebor Huang
1e4f11a6ce Merge branch 'main' of https://github.com/Trebor-Huang/Techmino into main 2021-08-01 02:03:57 +08:00
MrZ626
36b9dcaf43 修复没有自定义游戏的场地数据等文件在启动时会直接报错 2021-08-01 01:25:33 +08:00
MrZ626
ad3aff6a50 修改更新历史,整理代码 2021-08-01 00:49:20 +08:00
MrZ626
3bd6da6276 鼠标松开时如果有选中的控件就不触发场景的鼠标松开/点击事件 2021-08-01 00:44:09 +08:00
Trebor Huang
3ccc8cdd7b 增加OS X支持 (#154)
需要CCloader.dylib以及*.icns格式的图标。同时要按照love官网的教程打包游戏为*.app形态,修改Info.plist。
我暂时没有办法让游戏在*.love的形态下加载dylib。但是以文件夹形式可以直接将dylib文件放在根目录;app形式可以放在Framworks处。
我稍后会在 https://github.com/26F-Studio/cold_clear_ai_love2d_wrapper 详细描述得到CCloader.dylib的办法。
2021-07-31 23:42:41 +08:00
Trebor Huang
501f3a4eec 增加OS X支持
需要CCloader.dylib以及*.icns格式的图标。同时要按照love官网的教程打包游戏为*.app形态,修改Info.plist。
我暂时没有办法让游戏在*.love的形态下加载dylib。但是以文件夹形式可以直接将dylib文件放在根目录;app形式可以放在Framworks处。
我稍后会在 https://github.com/26F-Studio/cold_clear_ai_love2d_wrapper 详细描述得到CCloader.dylib的办法。
2021-07-31 23:00:16 +08:00
MrZ626
cfc6f65da5 游戏启动的时候检测配色不能为炸弹格 close #147 2021-07-31 21:49:40 +08:00
MrZ626
5853ac1823 马拉松模式添加倒计时线 close #153 2021-07-31 20:24:44 +08:00
MrZ626
3057b2a12f master-ex新增段位点显示 close #149 2021-07-31 20:00:13 +08:00
MrZ626
9ce90b76a4 应本人要求修改一个赞助id 2021-07-30 00:00:10 +08:00
MrZ626
e016a20c21 STRING模块新增两个编解码函数 2021-07-29 15:26:37 +08:00
user670
8fb8352c8d Update dict_en.lua (#145) 2021-07-28 03:16:52 +08:00
MrZ626
ed7ecd98c4 整理代码,修改更新历史 2021-07-28 03:15:05 +08:00
MrZ626
512c78e192 自定义游戏的序列任务场地等数据退出后会保存 2021-07-28 03:10:29 +08:00
MrZ626
81b3082087 修复数据升级时两个20G模式不正确 2021-07-27 14:52:03 +08:00
MrZ626
6fff929856 更新框架,aDraw模块改名gcExtend 2021-07-26 17:30:35 +08:00
MrZ626
e636deb08e 修改更新历史 2021-07-26 17:07:28 +08:00
MrZ626
464d5bedda 完善控制台内部分命令的描述文本 2021-07-26 17:07:13 +08:00
MrZ626
9cc70d4212 微调两个文档 2021-07-26 03:10:11 +08:00
MrZ626
737cdb74bd 中文词典添加(修改)旋转系统与说明并给英文词典留好位置 2021-07-26 03:02:18 +08:00
MrZ626
a833139e13 修改更新历史和build号 2021-07-26 01:25:29 +08:00
MrZ626
4ec9377f78 整理代码 2021-07-26 01:25:26 +08:00
MrZ626
e9e96f287f 修复image模块加载图片组会报错 2021-07-26 01:25:18 +08:00
MrZ626
57745f5d0a 回放时版面遮挡会变成半透明 close #143 2021-07-25 23:33:04 +08:00
MrZ626
515c2d1f60 COLOR模块的彩虹函数支持补充alpha参数(直接返回,保证格式) 2021-07-25 23:32:29 +08:00
MrZ626
decbde8d63 修复BiRS的J和L的1/3状态180度旋转用表错误 2021-07-25 23:16:38 +08:00
MrZ626
08c892d4ff TRS的Ospin表增加SZ按反时的尝试 2021-07-25 22:20:41 +08:00
MrZ626
850a31d172 BRS在程序内名称改为BiRS(防止和BPS-RS歧义)
修正BiRS中Z5和S5的180度转的表使用错误
整理代码
2021-07-25 22:07:01 +08:00
MrZ626
6ae419eeee 特别感谢名单添加yuhao7370 2021-07-25 03:00:33 +08:00
MrZ626
40bae13411 移除badapple背景 2021-07-25 02:54:47 +08:00
MrZ626
61946fe52e 整理代码 2021-07-25 02:54:47 +08:00
MrZ626
27cede0fad 优化游戏场景性能,移除回放按钮hideF函数 2021-07-25 01:43:22 +08:00
MrZ626
adae63eabb 修改更新历史和build号 2021-07-25 01:14:03 +08:00
MrZ626
3ff5f74af7 BRS改名BRS(Bias RS)
调整BRS的O的0→2,2→0踢墙表为无水平踢表
再调整BRS踢墙过滤条件,有偏移时不再禁止上踢,水平方向上偏移和踢墙偏移允许反向,但偏移和总位移不能反向
2021-07-25 00:53:04 +08:00
MrZ626
c3c151b375 小程序cubefield的碰撞判定移出draw,解决低绘制帧率导致漏判定的问题 close #138
(低逻辑帧率还是会漏)
2021-07-24 18:23:21 +08:00
MrZ626
2163d09c08 修复序列和任务超长导致渲染开销太大卡死 close #137 2021-07-24 16:42:31 +08:00
MrZ626
ea70c2ef9e 修改更新历史和赞助者名单 2021-07-24 15:52:47 +08:00
MrZ626
53f949571e ZRS改名BRS(Boost RS) 2021-07-24 15:49:24 +08:00
MrZ626
1d64a6b799 再调整ZRS(修改过滤条件,最终位移距离不超过√5并且禁止踢墙方向和水平偏移反向) 2021-07-24 15:49:21 +08:00
MrZ626
84b5790ab2 再升级websocket模块 2021-07-24 15:49:17 +08:00
MrZ626
6aa8de3506 调整zrs踢墙表 2021-07-24 15:49:14 +08:00
MrZ626
c1b55139b6 整理代码 2021-07-24 15:49:09 +08:00
MrZ626
670417dc6a 修改更新历史和build号 2021-07-24 15:49:06 +08:00
MrZ626
bd1d1f8ae4 添加应用所有设置的函数,修复导入设置后部分设置不生效 2021-07-24 15:49:03 +08:00
MrZ626
29a922e41f 大师l/u改为n/h(两个旧模式文件为看录像保留)
n难度新增500~1000,使用新bgm:secret8th remix
h难度降低时间门槛
2021-07-24 15:48:59 +08:00
MrZ626
ac9fd5e618 调整五首bgm 2021-07-24 15:48:48 +08:00
MrZ626
9d6a74680a 调整TRS中S5和Z5的踢墙表 2021-07-22 22:27:04 +08:00
MrZ626
9d52cf27d8 整理代码 2021-07-22 00:14:24 +08:00
huaji2369
35c38387e1 在不爆炸的前提下减少AI与自定义序列同开的限制 (#136) 2021-07-22 00:11:25 +08:00
MrZ626
908997ddef 调整生存n的bgm 2021-07-22 00:09:14 +08:00
MrZ626
cf0b95e955 新BGM:there(用于挖掘) 2021-07-22 00:08:47 +08:00
MrZ626
5bf5d44c96 旋转系统可以开关每个方块是否显示旋转中心 2021-07-21 16:29:04 +08:00
MrZ626
854776dac0 继续微调ZRS(修复合成dx绝对值最大限制计算错误) 2021-07-21 16:24:52 +08:00
MrZ626
6e1ba35ca3 修改更新历史和build号 2021-07-21 15:53:01 +08:00
MrZ626
a5a41e3b0c 修复触屏设置在窗口非默认长宽比时边缘网格缺失 2021-07-21 15:52:35 +08:00
MrZ626
e78114dd53 改进debug模式下光标位置显示 2021-07-21 15:33:07 +08:00
MrZ626
6174f3709c 修复视频设置里影子预览导致的报错 2021-07-21 15:10:36 +08:00
MrZ626
7f1f9b0221 修复有屏幕滚动的场景按住鼠标拖动时控件会失去焦点 2021-07-21 15:03:31 +08:00
MrZ626
0af4e2adb9 修改更新历史和build号 2021-07-21 04:44:51 +08:00
MrZ626
d5ab596749 移除SFX和VOC模块的loadOne方法 2021-07-21 04:40:20 +08:00
MrZ626
3d128d4850 删除多余的加载文本 2021-07-21 04:39:53 +08:00
MrZ626
46aa6fcc48 新BGM:beat5th(用于竞速五连块) 2021-07-21 04:39:33 +08:00
MrZ626
60d1eb4e3c 升级SKIN模块,不再需要在启动时就加载好方块贴图资源 2021-07-21 04:37:35 +08:00
MrZ626
4b2c55d90e 升级image模块,不再需要在启动时就加载好图片资源 2021-07-21 02:45:56 +08:00
MrZ626
0023c0a4c6 升级bgm模块,不再需要在启动时就加载好音乐资源 2021-07-21 02:36:11 +08:00
MrZ626
0265793a3f 整理socket库代码 2021-07-21 00:52:06 +08:00
MrZ626
b99d247ba5 大型重构websocket模块 2021-07-20 21:20:47 +08:00
MrZ626
bdc1e592a7 控制台移除移除水印的命令 2021-07-20 20:11:43 +08:00
MrZ626
d3ef7e7f81 整理代码 2021-07-20 15:16:52 +08:00
user670
78dfec15d6 Adjust the English in a console command 2021-07-20 15:07:10 +08:00
MrZ626
7a824e09a3 控制台resetall命令删除文件时机改为退出前最后一瞬间 close #133 2021-07-20 14:03:30 +08:00
MrZ626
7c58355048 调整中文和yygq加载完成文本 2021-07-20 14:01:59 +08:00
user670
89662e7e2c adjust lang_en -> loadText.finish 2021-07-20 14:00:15 +08:00
MrZ626
718fc750d9 websocket的子线程代码分离至单独文件并移除debugMode 2021-07-20 02:44:01 +08:00
MrZ626
9e143fbb73 整理代码 2021-07-20 02:39:15 +08:00
MrZ626
c561181bdf NET模块收到closeMessage时弹出的断开消息格式修改 2021-07-20 01:04:16 +08:00
MrZ626
b45920109f 尝试捕捉一个错误的具体位置 2021-07-19 16:51:08 +08:00
MrZ626
07290fe7ce 调整中英tip 2021-07-19 16:14:26 +08:00
MrZ626
944f57b04a 微调main文件开头说明 2021-07-19 15:37:56 +08:00
MrZ626
4079c6596e 调整中文tip 2021-07-19 15:36:05 +08:00
MrZ626
defe6c4f26 合并load和intro场景 2021-07-19 15:34:28 +08:00
MrZ626
ed2a46e059 intro动画加入一点颜色 2021-07-19 02:12:05 +08:00
MrZ626
498a0ef7e8 几个音频模块和skin模块load附加必须先init的条件 2021-07-18 23:33:45 +08:00
MrZ626
06d34d8c55 优化加载动画 2021-07-18 17:17:28 +08:00
MrZ626
cd670212a2 修改更新历史,补上部分issue编号 2021-07-18 16:36:52 +08:00
MrZ626
41e58e0bd6 修复marathon_bfmax死亡判定不合适 close #127 2021-07-18 16:16:39 +08:00
MrZ626
b0af47a422 master-u模式的500限制时间为183秒 2021-07-18 02:02:06 +08:00
MrZ626
ccfb0c72dd dropper添加一个请勿修改语法错误的注释(纪念意义) 2021-07-18 01:39:10 +08:00
MrZ626
be1b87a1af 修改特别感谢列表 2021-07-18 00:52:05 +08:00
user670
33ffb80241 Make languages directly use plrual for "X players remaining" (#128) 2021-07-18 00:47:39 +08:00
MrZ_26
42b61af93d Merge pull request #125 from 26F-Studio/user670-patch-20210717-eng-lang-fix
Update lang_en.lua
2021-07-17 05:23:04 +08:00
user670
cfdba225e0 Update lang_en.lua
updated the loadtext thing
2021-07-17 05:17:25 +08:00
user670
8c0b3fd31d Update lang_en.lua
Remove an extra full stop
2021-07-17 04:32:42 +08:00
MrZ626
ef88d3e437 新增noInitSZO模式参数 close #121 2021-07-17 02:29:33 +08:00
MrZ626
cbbb04655b 修复加载场景点鼠标报错 2021-07-17 02:23:42 +08:00
MrZ626
956b768475 再调整ZRS系统(新增±2,0踢墙),整理代码 2021-07-17 02:02:53 +08:00
MrZ626
51768a5a27 限制最大自定义序列长度(2600) close #122 2021-07-17 01:48:36 +08:00
MrZ626
4a58967590 修改更新历史和build号 2021-07-17 01:44:01 +08:00
MrZ626
bc879ee8e2 修复粘贴序列检测到损坏时没有重置光标位置导致后续操作出现问题 close #89 2021-07-17 01:41:16 +08:00
MrZ626
d3046fa588 完全取消加载动画 2021-07-17 01:38:27 +08:00
MrZ626
ce8fefe9f8 再调整ZRS系统(启用偏移条件改为当前状态是否顶墙而不是空转后状态) 2021-07-17 01:38:21 +08:00
MrZ626
f7369ef4ae 修复SKIN模块加载完成后忘了删除loadAll函数 2021-07-17 00:25:50 +08:00
MrZ626
c0cfb97034 移除水印 2021-07-17 00:24:07 +08:00
MrZ626
c742e9fd31 新增ASC和ASCplus(添加180度踢墙,实验性)旋转系统 2021-07-17 00:00:17 +08:00
MrZ626
1d1522a9c4 再微调ZRS踢墙表(修改有偏移时只允许y<0踢为允许y<=0踢) 2021-07-16 23:01:07 +08:00
MrZ626
a9925b3f15 再微调ZRS踢墙表(添加±1,2) 2021-07-16 21:47:39 +08:00
MrZ626
2ea9a58a41 新BGM:here(用于生存第五难度) 2021-07-16 17:02:35 +08:00
MrZ626
9abf7bb45b 修复控制台print命令输入非文件报错 close #124 2021-07-16 16:54:48 +08:00
MrZ626
6afaf462f8 再微调ZRS踢墙表 2021-07-15 23:54:48 +08:00
MrZ626
b1ac913dd8 更新ZRS,修改O和X的旋转踢墙方向 2021-07-14 23:24:43 +08:00
MrZ626
4e5b16c0e2 更新ZRS,移动键顶墙才会增加额外偏移 2021-07-14 22:26:20 +08:00
MrZ626
56b2a41eee 增加滑条控件测试声音的间隔 2021-07-14 18:58:37 +08:00
MrZ626
8b32f29c2a 控制台的flag添加sudo密码 2021-07-14 18:56:54 +08:00
MrZ626
52ad2e2ddc 修正只有屏幕宽度异常时自动刷新窗口尺寸 2021-07-14 18:51:13 +08:00
MrZ626
2edd5542f8 整理代码 2021-07-14 17:35:33 +08:00
MrZ626
cb27f145a3 开启msaa(实验性),修改更新历史和版本名 2021-07-14 17:09:05 +08:00
MrZ626
44cbe58486 控制台新增sudo(su)命令 2021-07-14 16:19:56 +08:00
MrZ626
1c8844c3c4 选择系统新增ZRS(实验性) 2021-07-14 00:06:22 +08:00
MrZ626
6c864ea59a 修正c2sym旋转系统一个内部小问题 2021-07-13 23:06:57 +08:00
MrZ626
9818685856 整理代码 2021-07-13 22:26:10 +08:00
MrZ626
51e709acf6 修复地图上两个无尽模式每次启动都会消失 2021-07-13 22:25:50 +08:00
MrZ626
f826899f45 修改debug模式鼠标位置显示方式 2021-07-13 16:08:49 +08:00
MrZ626
b3f9aa3d28 声音设置界面添加静音按钮 2021-07-13 15:25:00 +08:00
MrZ626
d9c31f6661 修复转换弄反20G模式数据时可能报错 2021-07-13 01:22:22 +08:00
MrZ626
2af3f15997 修复das为0时预览动画不正确 2021-07-13 00:34:45 +08:00
MrZ626
701e4bbdbb 新增小亚语音包(立绘等待更新) 2021-07-13 00:29:16 +08:00
MrZ626
ce8e2597fe 修复存档转换时两个20G模式数据弄反,更新版本号至0.16.0 2021-07-11 17:05:16 +08:00
MrZ626
b185852271 不再自动转换0.15.0以前存档 2021-07-11 16:58:13 +08:00
MrZ626
7a2ac914df 修复20G不会禁用各种软降键 2021-07-11 16:35:49 +08:00
MrZ626
a0e3eb21c5 主菜单按esc可以返回intro 2021-07-11 15:14:02 +08:00
MrZ626
c9132b02a4 修复更新存档时两个master内部名弄反 2021-07-11 15:00:44 +08:00
MrZ626
0e81b0f8c8 bgm nil微调 2021-07-11 15:00:44 +08:00
MrZ626
de3bd91d4d 新增bgm:shift(用于生存后三个难度) 2021-07-11 15:00:17 +08:00
293 changed files with 4739 additions and 3866 deletions

View File

@@ -0,0 +1,9 @@
---
name: Bug report (bluescreen crash) Bug报告 (蓝屏报错)
about: Create a report of problems which made the crash with a bluescreen
---
Screenshot with crash information:
*Image Here*
If you can reproduce it, write the steps here. If you can't, try to describe the exactly time the game crash, like pressing which key or which button:
*Details Here*

View File

@@ -0,0 +1,9 @@
---
name: Bug report (unintended behaviors) Bug报告 (奇怪的现象)
about: Create a report of unintended behaviors
---
Screenshot with unintended behaviors:
*Image(s) Here*
If you can reproduce it, write the steps here. If you can't, try to describe the exactly time the game crash, like pressing which key or which button:
*Details Here*

View File

@@ -0,0 +1,4 @@
---
name: Feature Request 添加新功能
about: Suggest an idea that may improve Techmino 提一些有意思的新想法,让Techmino越来越好!
---

View File

@@ -9,6 +9,17 @@ jobs:
runs-on: windows-latest
steps:
- uses: actions/checkout@v2
- name: Get CommitID
run: |
$CommitID=git rev-parse --short "${{ GITHUB.SHA }}"
echo "CommitID=${CommitID}" >> $env:GITHUB_ENV
- name: Get Version
run: |
$Version=python .github/workflows/getVersion.py
echo "Version=${Version}" >> $env:GITHUB_ENV
- name: Update Conf Version
run: |
python .github/workflows/updateConfVersion.py -H ${{ env.CommitID }}
- name: Download love
run: |
curl -OL https://github.com/love2d/love/releases/download/11.3/love-11.3-win64.zip
@@ -26,16 +37,27 @@ jobs:
copy /b love-11.3-win64\love.exe + game.love love-11.3-win64\Techmino.exe
del love-11.3-win64\love.exe
del love-11.3-win64\lovec.exe
- name: Artifact
uses: actions/upload-artifact@v1.0.0
- name: Upload
uses: actions/upload-artifact@v2
with:
name: Windows
name: Techmino_${{ env.Version }}_${{ env.CommitID }}_Windows
path: love-11.3-win64
build-linux:
runs-on: ubuntu-20.04
steps:
- uses: actions/checkout@v2
- name: Get CommitID
run: |
CommitID=$(git rev-parse --short "${{ GITHUB.SHA }}")
echo "CommitID=${CommitID}" >> $GITHUB_ENV
- name: Get Version
run: |
Version=$(python3 .github/workflows/getVersion.py)
echo "Version=${Version}" >> $GITHUB_ENV
- name: Update Conf Version
run: |
python3 .github/workflows/updateConfVersion.py -H ${{ env.CommitID }}
- name: Download AppImageKit
run: curl -OL https://github.com/AppImage/AppImageKit/releases/download/12/appimagetool-x86_64.AppImage
- name: Unpack and Repack
@@ -49,16 +71,27 @@ jobs:
cd ../../../..
cp -r document media parts Zframework conf.lua font.ttf main.lua squashfs-root/usr/share/Techmino
./appimagetool-x86_64.AppImage squashfs-root Techmino.AppImage
- name: Artifact
- name: Upload
uses: actions/upload-artifact@v2
with:
name: Linux
name: Techmino_${{ env.Version }}_${{ env.CommitID }}_Linux
path: Techmino.AppImage
build-android:
runs-on: ubuntu-20.04
steps:
- uses: actions/checkout@v2
- name: Get CommitID
run: |
CommitID=$(git rev-parse --short "${{ GITHUB.SHA }}")
echo "CommitID=${CommitID}" >> $GITHUB_ENV
- name: Get Version
run: |
Version=$(python3 .github/workflows/getVersion.py)
echo "Version=${Version}" >> $GITHUB_ENV
- name: Update Conf Version
run: |
python3 .github/workflows/updateConfVersion.py -H ${{ env.CommitID }}
- name: Download Apktool
run: curl -OL https://bitbucket.org/iBotPeaches/apktool/downloads/apktool_2.5.0.jar
- name: Unpack and Repack
@@ -68,10 +101,10 @@ jobs:
7z x -o. apk/assets/game.love libAndroid
rm apk/assets/game.love Techmino.apk
7z a -tzip apk/assets/game.love document libAndroid media parts Zframework conf.lua font.ttf main.lua
python3 .github/workflows/updateVersion.py
python3 .github/workflows/updateAndroidVersion.py
java -jar apktool_2.5.0.jar b -o Techmino.apk apk
- uses: 26F-Studio/sign-android-release@master
name: Sign app APK
name: Sign APK
id: sign_app
with:
releaseDirectory: .
@@ -81,8 +114,58 @@ jobs:
keyPassword: ${{ secrets.KEY_PASSWORD }}
env:
BUILD_TOOLS_VERSION: "30.0.2"
- name: Artifact
- name: Upload
uses: actions/upload-artifact@v2
with:
name: Android
name: Techmino_${{ env.Version }}_${{ env.CommitID }}_Android
path: ${{steps.sign_app.outputs.signedReleaseFile}}
build-macOS:
runs-on: macos-10.15
steps:
- uses: actions/checkout@v2
- name: Get CommitID
run: |
CommitID=$(git rev-parse --short "${{ GITHUB.SHA }}")
echo "CommitID=${CommitID}" >> $GITHUB_ENV
- name: Get Version
run: |
Version=$(python3 .github/workflows/getVersion.py)
echo "Version=${Version}" >> $GITHUB_ENV
- name: Update Conf Version
run: |
python3 .github/workflows/updateConfVersion.py -H ${{ env.CommitID }}
- name: Pack love
run: |
zip -r Techmino.love document media parts Zframework conf.lua font.ttf main.lua
- name: Download template
run: |
curl -OL https://github.com/26F-Studio/Techmino/releases/download/v0.15.1/Techmino.app.zip
unzip Techmino.app.zip
- name: Modify template
run: |
python3 .github/workflows/updateOSXVersion.py
mv Techmino.love Techmino.app/Contents/Resources
- name: Codesign executable
# In secrets:
# - MACOS_CERTIFICATE: the *.p12 Developer ID Certificate, encoded in base64
# - MACOS_CERTIFICATE_PWD: The password
env:
MACOS_CERTIFICATE: ${{ secrets.MACOS_CERTIFICATE }}
MACOS_CERTIFICATE_PWD: ${{ secrets.MACOS_CERTIFICATE_PWD }}
run: |
echo $MACOS_CERTIFICATE | base64 --decode > certificate.p12
security create-keychain -p Techminohaowan build.keychain
security default-keychain -s build.keychain
security unlock-keychain -p Techminohaowan build.keychain
security import certificate.p12 -k build.keychain -P $MACOS_CERTIFICATE_PWD -T /usr/bin/codesign
security set-key-partition-list -S apple-tool:,apple:,codesign: -s -k Techminohaowan build.keychain
/usr/bin/codesign --force --deep -s 79B81FC5EA155243C973B5417B0996501F00EF55 ./Techmino.app -v
- name: Pack Techmino
run: |
zip -r -y Techmino-Packed.app.zip Techmino.app
- name: Upload
uses: actions/upload-artifact@v2
with:
name: Techmino_${{ env.Version }}_${{ env.CommitID }}_macOS
path: Techmino-Packed.app.zip

11
.github/workflows/getVersion.py vendored Normal file
View File

@@ -0,0 +1,11 @@
import re
def getVersion():
with open("conf.lua", "r", encoding="utf-8") as file:
data = file.read()
versionCode = re.search("build=(\\d+)", data).group(1)
versionName = re.search('(?<=string=").*(?=@)', data).group()
return versionCode, versionName
if __name__ == "__main__":
versionCode, versionName = getVersion()
print (versionName)

View File

@@ -1,12 +1,12 @@
import re
with open("conf.lua", "r") as file:
data = file.read()
versionCode = re.search("build=(\\d+)", data).group(1)
versionName = re.search('short="([^"]+)', data).group(1)
import getVersion
versionCode, versionName = getVersion.getVersion()
with open("apk/apktool.yml", "r+") as file:
data = file.read()
data = re.sub("versionCode:.+", f"versionCode: '{versionCode}'", data)
data = re.sub("versionName:.+", f"versionName: {versionName}", data)
file.seek(0)
file.truncate()
file.write(data)
file.write(data)

13
.github/workflows/updateConfVersion.py vendored Normal file
View File

@@ -0,0 +1,13 @@
import argparse
if __name__ == "__main__":
parser = argparse.ArgumentParser(description="用于更新conf.lua内编译版本号")
parser.add_argument("-H", "--Hash", type=str, help = "Github提交Hash")
args = parser.parse_args()
with open("conf.lua", "r+", encoding="utf-8") as file:
data = file.read()
data = data.replace('@DEV', f'@{args.Hash[0:4]}')
file.seek(0)
file.truncate()
file.flush()
file.write(data)

65
.github/workflows/updateOSXVersion.py vendored Normal file
View File

@@ -0,0 +1,65 @@
import datetime
import getVersion
info = r"""<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>BuildMachineOSBuild</key>
<string>19B88</string>
<key>CFBundleDevelopmentRegion</key>
<string>English</string>
<key>CFBundleExecutable</key>
<string>love</string>
<key>CFBundleIconFile</key>
<string>iconfile</string>
<key>CFBundleIdentifier</key>
<string>org.love2d.MrZ.Techmino</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>Techmino</string>
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleShortVersionString</key>
<string>%s</string>
<key>CFBundleSignature</key>
<string>LoVe</string>
<key>CFBundleSupportedPlatforms</key>
<array>
<string>MacOSX</string>
</array>
<key>DTCompiler</key>
<string>com.apple.compilers.llvm.clang.1_0</string>
<key>DTPlatformBuild</key>
<string>11C504</string>
<key>DTPlatformVersion</key>
<string>GM</string>
<key>DTSDKBuild</key>
<string>19B90</string>
<key>DTSDKName</key>
<string>macosx10.15</string>
<key>DTXcode</key>
<string>1130</string>
<key>DTXcodeBuild</key>
<string>11C504</string>
<key>LSApplicationCategoryType</key>
<string>public.app-category.games</string>
<key>LSMinimumSystemVersion</key>
<string>10.7</string>
<key>NSHighResolutionCapable</key>
<true/>
<key>NSHumanReadableCopyright</key>
<string>©2020-%d 26F Studio, GNU LGPLv3.0</string>
<key>NSPrincipalClass</key>
<string>NSApplication</string>
<key>NSSupportsAutomaticGraphicsSwitching</key>
<false/>
</dict>
</plist>
"""
versionCode, versionName = getVersion.getVersion()
print("Updating to", versionName)
with open("Techmino.app/Contents/info.plist", "w") as file:
file.write(info % (versionName, datetime.datetime.today().year))

View File

@@ -5,4 +5,4 @@
集合各种现代方块规则,更多玩法,全新体验。
官网(建设中) https://home.techmino.org
官网(建设中) http://home.techmino.org

View File

@@ -1,17 +0,0 @@
local printf=love.graphics.printf
local draw=love.graphics.draw
local aDraw={}
function aDraw.str(obj,x,y)printf(obj,x-626,y,1252,'center')end
function aDraw.simpX(obj,x,y)draw(obj,x-obj:getWidth()*.5,y)end
function aDraw.simpY(obj,x,y)draw(obj,x,y-obj:getHeight()*.5)end
function aDraw.X(obj,x,y,a,k)draw(obj,x,y,a,k,nil,obj:getWidth()*.5,0)end
function aDraw.Y(obj,x,y,a,k)draw(obj,x,y,a,k,nil,0,obj:getHeight()*.5)end
function aDraw.draw(obj,x,y,a,k)draw(obj,x,y,a,k,nil,obj:getWidth()*.5,obj:getHeight()*.5)end
function aDraw.outDraw(obj,div,x,y,a,k)
local w,h=obj:getWidth()*.5,obj:getHeight()*.5
draw(obj,x-div,y-div,a,k,nil,w,h)
draw(obj,x-div,y+div,a,k,nil,w,h)
draw(obj,x+div,y-div,a,k,nil,w,h)
draw(obj,x+div,y+div,a,k,nil,w,h)
end
return aDraw

View File

@@ -1,6 +1,6 @@
local gc_clear=love.graphics.clear
local BGs={
none={draw=function()gc_clear(.15,.15,.15)end}
none={draw=function()gc_clear(.08,.08,.084)end}
}
local BGlist={'none'}
local BG={

View File

@@ -1,6 +1,6 @@
local BGM={
default=false,
getList=function()error("Can't getList before initialized!")end,
getList=function()error("Cannot getList before initialize!")end,
getCount=function()return 0 end,
play=NULL,
freshVolume=NULL,
@@ -13,10 +13,19 @@ function BGM.setDefault(bgm)
end
function BGM.init(list)
BGM.init=nil
local min=math.min
local Sources={}function BGM.getList()return list end
local Sources={}
local simpList={}
for _,v in next,list do
table.insert(simpList,v.name)
Sources[v.name]=v.path
end
table.sort(simpList)
function BGM.getList()return simpList end
local count=#simpList
function BGM.getCount()return count end
function BGM.loadAll()for name in next,Sources do load(name)end end
local count=#list function BGM.getCount()return count end
local function fadeOut(src)
while true do
coroutine.yield()
@@ -32,7 +41,7 @@ function BGM.init(list)
while true do
coroutine.yield()
local v=SETTING.bgm
v=min(v,src:getVolume()+.025*v)
v=math.min(v,src:getVolume()+.025*v)
src:setVolume(v)
if v>=SETTING.bgm then
return true
@@ -42,62 +51,59 @@ function BGM.init(list)
local function removeCurFadeOut(task,code,src)
return task.code==code and task.args[1]==src
end
local function load(skip)
for i=1,count do
local file='media/BGM/'..list[i]..'.ogg'
if love.filesystem.getInfo(file)then
Sources[list[i]]=love.audio.newSource(file,'stream')
Sources[list[i]]:setLooping(true)
Sources[list[i]]:setVolume(0)
local function load(name)
if type(Sources[name])=='string'then
if love.filesystem.getInfo(Sources[name])then
Sources[name]=love.audio.newSource(Sources[name],'stream')
Sources[name]:setLooping(true)
Sources[name]:setVolume(0)
return true
else
MES.new('warn',"No BGM file: "..list[i],5)
MES.new('warn',"No BGM file: "..Sources[name],5)
end
if not skip and i~=count then
coroutine.yield()
end
end
BGM.loadOne=nil
function BGM.play(s)
if not s then s=BGM.default end
if SETTING.bgm==0 then
BGM.nowPlay=s
BGM.playing=Sources[s]
return true
end
if s and Sources[s]then
if BGM.nowPlay~=s then
if BGM.nowPlay then TASK.new(fadeOut,BGM.playing)end
TASK.removeTask_iterate(removeCurFadeOut,fadeOut,Sources[s])
TASK.removeTask_code(fadeIn)
TASK.new(fadeIn,Sources[s])
BGM.nowPlay=s
BGM.playing=Sources[s]
BGM.playing:play()
end
return true
end
end
function BGM.freshVolume()
if BGM.playing then
local v=SETTING.bgm
if v>0 then
BGM.playing:setVolume(v)
BGM.playing:play()
elseif BGM.nowPlay then
BGM.playing:pause()
end
end
end
function BGM.stop()
TASK.removeTask_code(fadeIn)
if BGM.nowPlay then TASK.new(fadeOut,BGM.playing)end
BGM.nowPlay,BGM.playing=nil
elseif Sources[name]then
return true
elseif name then
MES.new('warn',"No BGM: "..name,5)
end
end
function BGM.play(name)
if not name then name=BGM.default end
if not load(name)then return end
if SETTING.bgm==0 then
BGM.nowPlay=name
BGM.playing=Sources[name]
return true
end
if name and Sources[name]then
if BGM.nowPlay~=name then
if BGM.nowPlay then TASK.new(fadeOut,BGM.playing)end
TASK.removeTask_iterate(removeCurFadeOut,fadeOut,Sources[name])
TASK.removeTask_code(fadeIn)
BGM.loadOne=coroutine.wrap(load)
function BGM.loadAll()load(true)end
TASK.new(fadeIn,Sources[name])
BGM.nowPlay=name
BGM.playing=Sources[name]
BGM.playing:play()
end
return true
end
end
function BGM.freshVolume()
if BGM.playing then
local v=SETTING.bgm
if v>0 then
BGM.playing:setVolume(v)
BGM.playing:play()
elseif BGM.nowPlay then
BGM.playing:pause()
end
end
end
function BGM.stop()
TASK.removeTask_code(fadeIn)
if BGM.nowPlay then TASK.new(fadeOut,BGM.playing)end
BGM.nowPlay,BGM.playing=nil
end
end
return BGM

View File

@@ -1,60 +1,60 @@
local COLOR={
red= {1.0, 0.0, 0.0},
fire= {1.0, 0.4, 0.0},
orange= {1.0, 0.6, 0.0},
yellow= {1.0, 1.0, 0.0},
lime= {0.7, 1.0, 0.0},
jade= {0.5, 1.0, 0.0},
green= {0.0, 1.0, 0.0},
aqua= {0.0, 1.0, 0.6},
cyan= {0.0, 1.0, 1.0},
navy= {0.0, 0.7, 1.0},
sea= {0.0, 0.4, 1.0},
blue= {0.2, 0.2, 1.0},
violet= {0.4, 0.0, 1.0},
purple= {0.7, 0.0, 1.0},
magenta= {1.0, 0.0, 1.0},
wine= {1.0, 0.0, 0.5},
red= {.92, .12, .12},
fire= {.92, 0.4, .12},
orange= {.92, 0.6, .12},
yellow= {.92, .92, .12},
lime= {0.7, .92, .12},
jade= {0.5, .92, .12},
green= {.12, .92, .12},
aqua= {.12, .92, 0.6},
cyan= {.12, .92, .92},
navy= {.12, 0.7, .92},
sea= {.12, 0.4, .92},
blue= {0.2, 0.2, .92},
violet= {0.4, .12, .92},
purple= {0.7, .12, .92},
magenta= {.92, .12, .92},
wine= {.92, .12, 0.5},
lRed= {1.0, 0.5, 0.5},
lFire= {1.0, 0.7, 0.5},
lOrange= {1.0, 0.8, 0.3},
lYellow= {1.0, 1.0, 0.5},
lLime= {0.8, 1.0, 0.4},
lJade= {0.6, 1.0, 0.4},
lGreen= {0.5, 1.0, 0.5},
lAqua= {0.4, 1.0, 0.7},
lCyan= {0.5, 1.0, 1.0},
lNavy= {0.5, 0.8, 1.0},
lSea= {0.4, 0.7, 1.0},
lBlue= {0.7, 0.7, 1.0},
lViolet= {0.7, 0.4, 1.0},
lPurple= {0.8, 0.4, 1.0},
lMagenta= {1.0, 0.5, 1.0},
lWine= {1.0, 0.4, 0.7},
lRed= {.95, 0.5, 0.5},
lFire= {.95, 0.7, 0.5},
lOrange= {.95, 0.8, 0.3},
lYellow= {.95, .95, 0.5},
lLime= {0.8, .95, 0.4},
lJade= {0.6, .95, 0.4},
lGreen= {0.5, .95, 0.5},
lAqua= {0.4, .95, 0.7},
lCyan= {0.5, .95, .95},
lNavy= {0.4, .85, .95},
lSea= {0.5, 0.7, .95},
lBlue= {0.7, 0.7, .95},
lViolet= {0.7, 0.4, .95},
lPurple= {0.8, 0.4, .95},
lMagenta= {.95, 0.5, .95},
lWine= {.95, 0.4, 0.7},
dRed= {0.6, 0.0, 0.0},
dFire= {0.6, 0.3, 0.0},
dOrange= {0.6, 0.4, 0.0},
dYellow= {0.6, 0.6, 0.0},
dLime= {0.5, 0.6, 0.0},
dJade= {0.3, 0.6, 0.0},
dGreen= {0.0, 0.6, 0.0},
dAqua= {0.0, 0.6, 0.4},
dCyan= {0.0, 0.6, 0.6},
dNavy= {0.0, 0.4, 0.6},
dSea= {0.0, 0.2, 0.6},
dRed= {0.6, .08, .08},
dFire= {0.6, 0.3, .08},
dOrange= {0.6, 0.4, .08},
dYellow= {0.6, 0.6, .08},
dLime= {0.5, 0.6, .08},
dJade= {0.3, 0.6, .08},
dGreen= {.08, 0.6, .08},
dAqua= {.08, 0.6, 0.4},
dCyan= {.08, 0.6, 0.6},
dNavy= {.08, 0.4, 0.6},
dSea= {.08, 0.2, 0.6},
dBlue= {0.1, 0.1, 0.6},
dViolet= {0.2, 0.0, 0.6},
dPurple= {0.4, 0.0, 0.6},
dMagenta= {0.6, 0.0, 0.6},
dWine= {0.6, 0.0, 0.3},
dViolet= {0.2, .08, 0.6},
dPurple= {0.4, .08, 0.6},
dMagenta= {0.6, .08, 0.6},
dWine= {0.6, .08, 0.3},
black= {0.0, 0.0, 0.0},
black= {.05, .05, .05},
dGray= {0.3, 0.3, 0.3},
gray= {0.6, 0.6, 0.6},
lGray= {0.8, 0.8, 0.8},
white= {1.0, 1.0, 1.0},
white= {.97, .97, .97},
}
for k,v in next,{
R='red',F='fire',O='orange',Y='yellow',L='lime',J='jade',G='green',A='aqua',C='cyan',N='navy',S='sea',B='blue',V='violet',P='purple',M='magenta',W='wine',
@@ -93,29 +93,33 @@ end
do--Rainbow generators
local sin=math.sin
function COLOR.rainbow(phase)
function COLOR.rainbow(phase,a)
return
sin(phase)*.4+.6,
sin(phase+2.0944)*.4+.6,
sin(phase-2.0944)*.4+.6
sin(phase-2.0944)*.4+.6,
a
end
function COLOR.rainbow_light(phase)
function COLOR.rainbow_light(phase,a)
return
sin(phase)*.2+.7,
sin(phase+2.0944)*.2+.7,
sin(phase-2.0944)*.2+.7
sin(phase-2.0944)*.2+.7,
a
end
function COLOR.rainbow_dark(phase)
function COLOR.rainbow_dark(phase,a)
return
sin(phase)*.2+.4,
sin(phase+2.0944)*.2+.4,
sin(phase-2.0944)*.2+.4
sin(phase-2.0944)*.2+.4,
a
end
function COLOR.rainbow_gray(phase)
function COLOR.rainbow_gray(phase,a)
return
sin(phase)*.16+.5,
sin(phase+2.0944)*.16+.5,
sin(phase-2.0944)*.16+.5
sin(phase-2.0944)*.16+.5,
a
end
end

View File

@@ -15,9 +15,9 @@ local cmds={
print="print",
setFT=setFont,
mText=ADRAW.str,
mDraw=ADRAW.draw,
mOutDraw=ADRAW.outDraw,
mText=GC.str,
mDraw=GC.draw,
mOutDraw=GC.outDraw,
draw="draw",
line="line",

View File

@@ -1,50 +0,0 @@
local find=string.find
local tabs={
[0]="",
"\t",
"\t\t",
"\t\t\t",
"\t\t\t\t",
"\t\t\t\t\t",
}
return function(L,t)
local s
if t then
s="{\n"
else
s="return{\n"
t=1
if type(L)~='table'then
return
end
end
local count=1
for k,v in next,L do
local T=type(k)
if T=='number'then
if k==count then
k=""
count=count+1
else
k="["..k.."]="
end
elseif T=='string'then
if find(k,"[^0-9a-zA-Z_]")then
k="[\""..k.."\"]="
else
k=k.."="
end
elseif T=='boolean'then k="["..k.."]="
else error("Error key type!")
end
T=type(v)
if T=='number'then v=tostring(v)
elseif T=='string'then v="\""..v.."\""
elseif T=='table'then v=TABLE.dump(v,t+1)
elseif T=='boolean'then v=tostring(v)
else error("Error data type!")
end
s=s..tabs[t]..k..v..",\n"
end
return s..tabs[t-1].."}"
end

View File

@@ -44,15 +44,20 @@ function FILE.save(data,name,mode)
data=tostring(data)
end
if mode:find'd'and fs.getInfo(name)then
MES.new('error',text.saveError_duplicate)
return
end
local F=fs.newFile(name)
F:open'w'
local success,mes=F:write(data)
F:flush()F:close()
if not success then
if success then
return true
else
MES.new('error',text.saveError..(mes or"unknown error"))
MES.traceback()
end
return success
end
function FILE.clear(path)
if fs.getRealDirectory(path)~=SAVEDIR or fs.getInfo(path).type~='directory'then return end

160
Zframework/gcExtend.lua Normal file
View File

@@ -0,0 +1,160 @@
local gc=love.graphics
local setColor=gc.setColor
local printf=gc.printf
local draw=gc.draw
local GC={}
function GC.str(obj,x,y)printf(obj,x-626,y,1252,'center')end
function GC.simpX(obj,x,y)draw(obj,x-obj:getWidth()*.5,y)end
function GC.simpY(obj,x,y)draw(obj,x,y-obj:getHeight()*.5)end
function GC.X(obj,x,y,a,k)draw(obj,x,y,a,k,nil,obj:getWidth()*.5,0)end
function GC.Y(obj,x,y,a,k)draw(obj,x,y,a,k,nil,0,obj:getHeight()*.5)end
function GC.draw(obj,x,y,a,k)draw(obj,x,y,a,k,nil,obj:getWidth()*.5,obj:getHeight()*.5)end
function GC.outDraw(obj,div,x,y,a,k)
local w,h=obj:getWidth()*.5,obj:getHeight()*.5
draw(obj,x-div,y-div,a,k,nil,w,h)
draw(obj,x-div,y+div,a,k,nil,w,h)
draw(obj,x+div,y-div,a,k,nil,w,h)
draw(obj,x+div,y+div,a,k,nil,w,h)
end
function GC.shadedPrint(str,x,y,mode,d,clr1,clr2)
local w=1280
if mode=='center'then
x=x-w*.5
elseif mode=='right'then
x=x-w
end
if not d then d=1 end
setColor(clr1 or COLOR.D)
printf(str,x-d,y-d,w,mode)
printf(str,x-d,y+d,w,mode)
printf(str,x+d,y-d,w,mode)
printf(str,x+d,y+d,w,mode)
setColor(clr2 or COLOR.Z)
printf(str,x,y,w,mode)
end
function GC.regularPolygon(mode,x,y,R,segments,r,phase)
local X,Y={},{}
local ang=phase or 0
local angStep=6.283185307179586/segments
for i=1,segments do
X[i]=x+R*math.cos(ang)
Y[i]=y+R*math.sin(ang)
ang=ang+angStep
end
X[segments+1]=x+R*math.cos(ang)
Y[segments+1]=y+R*math.sin(ang)
local halfAng=6.283185307179586/segments/2
local erasedLen=r*math.tan(halfAng)
if mode=='line'then
erasedLen=erasedLen+1--Fix 1px cover
for i=1,segments do
--Line
local x1,y1,x2,y2=X[i],Y[i],X[i+1],Y[i+1]
local dir=math.atan2(y2-y1,x2-x1)
gc.line(x1+erasedLen*math.cos(dir),y1+erasedLen*math.sin(dir),x2-erasedLen*math.cos(dir),y2-erasedLen*math.sin(dir))
--Arc
ang=ang+angStep
local R2=R-r/math.cos(halfAng)
local arcCX,arcCY=x+R2*math.cos(ang),y+R2*math.sin(ang)
gc.arc('line','open',arcCX,arcCY,r,ang-halfAng,ang+halfAng)
end
elseif mode=='fill'then
local L={}
for i=1,segments do
--Line
local x1,y1,x2,y2=X[i],Y[i],X[i+1],Y[i+1]
local dir=math.atan2(y2-y1,x2-x1)
table.insert(L,x1+erasedLen*math.cos(dir))
table.insert(L,y1+erasedLen*math.sin(dir))
table.insert(L,x2-erasedLen*math.cos(dir))
table.insert(L,y2-erasedLen*math.sin(dir))
--Arc
ang=ang+angStep
local R2=R-r/math.cos(halfAng)
local arcCX,arcCY=x+R2*math.cos(ang),y+R2*math.sin(ang)
gc.arc('fill','open',arcCX,arcCY,r,ang-halfAng,ang+halfAng)
end
gc.polygon('fill',L)
else
error("Draw mode should be 'line' or 'fill'")
end
end
do--function GC.DO(L)
local cmds={
origin="origin",
move="translate",
scale="scale",
rotate="rotate",
shear="shear",
clear="clear",
setCL="setColor",
setCM="setColorMask",
setLW="setLineWidth",
setLS="setLineStyle",
setLJ="setLineJoin",
print="print",
setFT=setFont,
mText=GC.str,
mDraw=GC.draw,
mOutDraw=GC.outDraw,
draw="draw",
line="line",
fRect=function(...)gc.rectangle('fill',...)end,
dRect=function(...)gc.rectangle('line',...)end,
fCirc=function(...)gc.circle('fill',...)end,
dCirc=function(...)gc.circle('line',...)end,
fElps=function(...)gc.ellipse('fill',...)end,
dElps=function(...)gc.ellipse('line',...)end,
fPoly=function(...)gc.polygon('fill',...)end,
dPoly=function(...)gc.polygon('line',...)end,
dPie=function(...)gc.arc('line',...)end,
dArc=function(...)gc.arc('line','open',...)end,
dBow=function(...)gc.arc('line','closed',...)end,
fPie=function(...)gc.arc('fill',...)end,
fArc=function(...)gc.arc('fill','open',...)end,
fBow=function(...)gc.arc('fill','closed',...)end,
fRPol=function(...)GC.regularPolygon('fill',...)end,
dRPol=function(...)GC.regularPolygon('line',...)end,
}
local sizeLimit=gc.getSystemLimits().texturesize
function GC.DO(L)
gc.push()
::REPEAT_tryAgain::
local success,canvas=pcall(gc.newCanvas,math.min(L[1],sizeLimit),math.min(L[2],sizeLimit))
if not success then
sizeLimit=math.floor(sizeLimit*.8)
goto REPEAT_tryAgain
end
gc.setCanvas(canvas)
gc.origin()
gc.setColor(1,1,1)
gc.setLineWidth(1)
for i=3,#L do
local cmd=L[i][1]
if type(cmd)=='boolean'and cmd then
table.remove(L[i],1)
cmd=L[i][1]
end
if type(cmd)=='string'then
local func=cmds[cmd]
if type(func)=='string'then func=gc[func]end
if func then
func(unpack(L[i],2))
else
error("No gc command: "..cmd)
end
end
end
gc.setCanvas()
gc.pop()
return canvas
end
end
return GC

View File

@@ -1,35 +1,26 @@
local IMG={
getCount=function()return 0 end,
}
local IMG={}
function IMG.init(list)
IMG.init=nil
local count=0
for k,v in next,list do
count=count+1
IMG[k]=v
end
function IMG.getCount()return count end
local function load(skip)
local loaded=0
for k,v in next,list do
if type(v)=='string'then
IMG[k]=love.graphics.newImage('media/image/'..v)
else
for i=1,#v do
v[i]=love.graphics.newImage('media/image/'..v[i])
end
IMG[k]=v
end
loaded=loaded+1
if not skip and loaded~=count then
coroutine.yield()
local null=love.graphics.newCanvas(1,1)
setmetatable(IMG,{__index=function(self,name)
if type(list[name])=='table'then
self[name]={}
for i=1,#list[name]do
self[name][i]=love.graphics.newImage(list[name][i])
end
elseif type(list[name])=='string'then
self[name]=love.graphics.newImage(list[name])
else
MES.new('warn',"No BGM: "..name,5)
self[name]=null
end
IMG.loadOne=nil
return self[name]
end})
function IMG.loadAll()
for k in next,list do local _=IMG[k]end
IMG.loadAll=nil
end
IMG.loadOne=coroutine.wrap(load)
function IMG.loadAll()load(true)end
end
return IMG

View File

@@ -3,17 +3,17 @@ EDITING=""
LOADED=false
ERRDATA={}
require'Zframework.setFont'
ADRAW=require'Zframework.aDraw'
mStr=ADRAW.str
mText=ADRAW.simpX
mDraw=ADRAW.draw
SCR= require'Zframework.screen'
COLOR= require'Zframework.color'
SCN= require'Zframework.scene'
WS= require'Zframework.websocket'
require'Zframework.setFont'
GC=require'Zframework.gcExtend'
mStr=GC.str
mText=GC.simpX
mDraw=GC.draw
LOADLIB=require'Zframework.loadLib'
WHEELMOV=require'Zframework.wheelScroll'
@@ -25,7 +25,6 @@ VIB= require'Zframework.vibrate'
SFX= require'Zframework.sfx'
LIGHT= require'Zframework.light'
DOGC= require'Zframework.doGC'
BG= require'Zframework.background'
WIDGET= require'Zframework.widget'
TEXT= require'Zframework.text'
@@ -45,7 +44,7 @@ THEME= require'Zframework.theme'
local ms,kb=love.mouse,love.keyboard
local gc=love.graphics
local gc_push,gc_pop,gc_clear=gc.push,gc.pop,gc.clear
local gc_push,gc_pop,gc_clear,gc_discard=gc.push,gc.pop,gc.clear,gc.discard
local gc_replaceTransform,gc_present=gc.replaceTransform,gc.present
local gc_setColor,gc_setLineWidth=gc.setColor,gc.setLineWidth
local gc_draw,gc_line,gc_print=gc.draw,gc.line,gc.print
@@ -66,7 +65,7 @@ joysticks={}
local devMode
local batteryImg=DOGC{31,20,
local batteryImg=GC.DO{31,20,
{'fRect',1,0,26,2},
{'fRect',1,18,26,2},
{'fRect',0,1,2,18},
@@ -97,12 +96,12 @@ local function updatePowerInfo()
gc.rectangle('fill',76,6,pow*.22,14)
if pow<100 then
setFont(15)
gc_setColor(0,0,0)
gc.setColor(COLOR.D)
gc_print(pow,77,1)
gc_print(pow,77,3)
gc_print(pow,79,1)
gc_print(pow,79,3)
gc_setColor(1,1,1)
gc_setColor(COLOR.Z)
gc_print(pow,78,2)
end
end
@@ -149,10 +148,13 @@ end
function love.mousereleased(x,y,k,touch)
if touch or SCN.swapping then return end
mx,my=ITP(xOy,x,y)
WIDGET.release(mx,my)
if SCN.mouseUp then SCN.mouseUp(mx,my,k)end
if lastX and SCN.mouseClick and(mx-lastX)^2+(my-lastY)^2<62 then
SCN.mouseClick(mx,my,k)
if WIDGET.sel then
WIDGET.release(mx,my)
else
if lastX and SCN.mouseClick and(mx-lastX)^2+(my-lastY)^2<62 then
SCN.mouseClick(mx,my,k)
end
end
end
function love.wheelmoved(x,y)
@@ -215,7 +217,7 @@ local function noDevkeyPressed(key)
elseif key=="f4"then
for _=1,8 do
local P=PLY_ALIVE[rnd(#PLY_ALIVE)]
if P~=PLAYERS[1]then
if P and P~=PLAYERS[1]then
P.lastRecv=PLAYERS[1]
P:lose()
end
@@ -471,6 +473,7 @@ function love.errorhandler(msg)
end
end
end
love.threaderror=nil
love.draw,love.update=nil--remove default draw/update
@@ -492,47 +495,50 @@ local wsBottomImage do
ins(L,{'setCL',1,1,1,i*.005})
ins(L,{'fRect',i,0,1,18})
end
wsBottomImage=DOGC(L)
wsBottomImage=GC.DO(L)
end
local ws_deadImg=DOGC{20,20,
local ws_deadImg=GC.DO{20,20,
{'setFT',20},
{'setCL',1,.3,.3},
{'print',"X",3,-4},
}
local ws_connectingImg=DOGC{20,20,
local ws_connectingImg=GC.DO{20,20,
{'setLW',3},
{'dArc',11.5,10,6.26,1,5.28},
}
local ws_runningImg=DOGC{20,20,
local ws_runningImg=GC.DO{20,20,
{'setFT',20},
{'setCL',.5,1,0},
{'print',"R",3,-4},
}
local cursorImg=DOGC{16,16,
{"fCirc",8,8,4},
{"setCL",1,1,1,.7},
{"fCirc",8,8,6},
local cursorImg=GC.DO{16,16,
{'fCirc',8,8,4},
{'setCL',1,1,1,.7},
{'fCirc',8,8,6},
}
local cursor_holdImg=DOGC{16,16,
{"setLW",2},
{"dCirc",8,8,7},
{"fCirc",8,8,3},
local cursor_holdImg=GC.DO{16,16,
{'setLW',2},
{'dCirc',8,8,7},
{'fCirc',8,8,3},
}
function love.run()
local love=love
local VOC,BG,SYSFX=VOC,BG,SYSFX
local TASK,TEXT=TASK,TEXT
local TEXTURE,TIME=TEXTURE,TIME
local SETTING,VERSION=SETTING,VERSION
local BG=BG
local TEXT_update,TEXT_draw=TEXT.update,TEXT.draw
local MES_update,MES_draw=MES.update,MES.draw
local WS_update=WS.update
local TASK_update=TASK.update
local SYSFX_update,SYSFX_draw=SYSFX.update,SYSFX.draw
local WIDGET_update,WIDGET_draw=WIDGET.update,WIDGET.draw
local STEP,WAIT=love.timer.step,love.timer.sleep
local FPS,MINI=love.timer.getFPS,love.window.isMinimized
local PUMP,POLL=love.event.pump,love.event.poll
local frameTimeList={}
local TIME,SETTING,VERSION=TIME,SETTING,VERSION
local frameTimeList={}
local lastFrame=TIME()
local lastFreshPow=lastFrame
local FCT=0--Framedraw counter, from 0~99
@@ -564,16 +570,16 @@ function love.run()
--UPDATE
STEP()
TASK.update()
WS.update(dt)
VOC.update()
BG.update(dt)
SYSFX.update(dt)
TEXT_update()
MES_update(dt)
WS_update(dt)
TASK_update()
SYSFX_update(dt)
if SCN.update then SCN.update(dt)end
if SCN.swapping then SCN.swapUpdate()end
WIDGET.update()
TEXT.update()
MES.update(dt)
WIDGET_update()
--DRAW
if not MINI()then
@@ -581,32 +587,33 @@ function love.run()
if FCT>=100 then
FCT=FCT-100
local safeX=SCR.safeX
gc_replaceTransform(SCR.origin)
gc_setColor(1,1,1)
BG.draw()
gc_replaceTransform(SCR.xOy)
if SCN.draw then SCN.draw()end
WIDGET.draw()
SYSFX.draw()
TEXT.draw()
WIDGET_draw()
SYSFX_draw()
TEXT_draw()
--Draw cursor
if mouseShow then
local R=int((time+1)/2)%7+1
_=minoColor[SETTING.skin[R]]
gc_setColor(_[1],_[2],_[3],min(abs(1-time%2),.3))
_=SCS[R][0]
_=DSCP[R][0]
gc_draw(TEXTURE.miniBlock[R],mx,my,time%3.14159265359*4,16,16,_[2]+.5,#BLOCKS[R][0]-_[1]-.5)
gc_setColor(1,1,1)
gc_draw(ms.isDown(1)and cursor_holdImg or cursorImg,mx,my,nil,nil,nil,8,8)
end
gc_replaceTransform(SCR.xOy_ul)
MES.draw()
MES_draw()
gc_replaceTransform(SCR.origin)
--Draw power info.
if SETTING.powerInfo then
gc_setColor(1,1,1)
gc_draw(infoCanvas,SCR.safeX,0,0,SCR.k)
gc_draw(infoCanvas,safeX,0,0,SCR.k)
end
--Draw scene swapping animation
@@ -624,17 +631,16 @@ function love.run()
--Draw FPS
setFont(15)
gc_setColor(1,1,1)
gc_print(FPS(),SCR.safeX+5,-20)
gc_print(FPS(),safeX+5,-20)
--Debug info.
if devMode then
--Left-down infos
gc_setColor(devColor[devMode])
gc_print("MEM "..gcinfo(),SCR.safeX+5,-40)
gc_print("Lines "..FREEROW.getCount(),SCR.safeX+5,-60)
gc_print("Cursor "..int(mx+.5).." "..int(my+.5),SCR.safeX+5,-80)
gc_print("Voices "..VOC.getQueueCount(),SCR.safeX+5,-100)
gc_print("Tasks "..TASK.getCount(),SCR.safeX+5,-120)
gc_print("MEM "..gcinfo(),safeX+5,-40)
gc_print("Lines "..FREEROW.getCount(),safeX+5,-60)
gc_print("Tasks "..TASK.getCount(),safeX+5,-80)
gc_print("Voices "..VOC.getQueueCount(),safeX+5,-100)
--Update & draw frame time
ins(frameTimeList,1,dt)rem(frameTimeList,126)
@@ -643,30 +649,44 @@ function love.run()
gc.rectangle('fill',150+2*i,-20,2,-frameTimeList[i]*4000)
end
--Cursor pos disp
gc_replaceTransform(SCR.origin)
local x,y=SCR.xOy:transformPoint(mx,my)
gc_setLineWidth(1)
gc_line(x,0,x,SCR.h)
gc_line(0,y,SCR.w,y)
local t=int(mx+.5)..","..int(my+.5)
gc.setColor(COLOR.D)
gc_print(t,x+1,y)
gc_print(t,x+1,y-1)
gc_print(t,x+2,y-1)
gc_setColor(COLOR.Z)
gc_print(t,x+2,y)
gc_replaceTransform(SCR.xOy_dr)
--Websocket status
for i=1,6 do
local status=WS.status(WSnames[i])
gc_setColor(1,1,1)
gc.draw(wsBottomImage,-79,20*i-139)
if status=='dead'then
gc_draw(ws_deadImg,-20,20*i-140)
elseif status=='connecting'then
gc_setColor(1,1,1,.5+.3*sin(time*6.26))
gc_draw(ws_connectingImg,-20,20*i-140)
elseif status=='running'then
gc_draw(ws_runningImg,-20,20*i-140)
--Websocket status
for i=1,6 do
local status=WS.status(WSnames[i])
gc_setColor(1,1,1)
gc.draw(wsBottomImage,-79,20*i-139)
if status=='dead'then
gc_draw(ws_deadImg,-20,20*i-140)
elseif status=='connecting'then
gc_setColor(1,1,1,.5+.3*sin(time*6.26))
gc_draw(ws_connectingImg,-20,20*i-140)
elseif status=='running'then
gc_draw(ws_runningImg,-20,20*i-140)
end
local t1,t2,t3=WS.getTimers(WSnames[i])
gc_setColor(.9,.9,.9,t1)gc.rectangle('fill',-60,20*i-122,-16,-16)
gc_setColor(.3,1,.3,t2)gc.rectangle('fill',-42,20*i-122,-16,-16)
gc_setColor(1,.2,.2,t3)gc.rectangle('fill',-24,20*i-122,-16,-16)
end
local t1,t2,t3=WS.getTimers(WSnames[i])
gc_setColor(1,1,1,t1)gc.rectangle('fill',-60,20*i-120,-20,-20)
gc_setColor(0,1,0,t2)gc.rectangle('fill',-40,20*i-120,-20,-20)
gc_setColor(1,0,0,t3)gc.rectangle('fill',-20,20*i-120,-20,-20)
end
end
gc_present()
--SPEED UPUPUP!
if SETTING.cleanCanvas then gc.discard()end
if SETTING.cleanCanvas then gc_discard()end
end
end
@@ -676,14 +696,18 @@ function love.run()
updatePowerInfo()
lastFreshPow=time
end
if gc.getWidth()~=SCR.w then
if gc.getWidth()~=SCR.w or gc.getHeight()~=SCR.h then
love.resize(gc.getWidth(),gc.getHeight())
end
end
--Slow devmode
if devMode==3 then WAIT(.1)
elseif devMode==4 then WAIT(.5)
if devMode then
if devMode==3 then
WAIT(.1)
elseif devMode==4 then
WAIT(.5)
end
end
--Keep 60fps

View File

@@ -34,6 +34,15 @@ return function(name,libName)
return
end
return libFunc()
elseif SYSTEM=="OS X" then
local rtn = package.loadlib(libName["OS X"], libName.libFunc)
if rtn then
local a = rtn()
MES.new('check',name.." lib loaded")
return a
else
MES.new('error',"Cannot load "..name)
end
else
MES.new('error',"No "..name.." for "..SYSTEM)
return

View File

@@ -6,7 +6,7 @@ local ins,rem=table.insert,table.remove
local mesList={}
local mesIcon={
check=DOGC{40,40,
check=GC.DO{40,40,
{'setLW',10},
{'setCL',0,0,0},
{'line',4,19,15,30,36,9},
@@ -14,7 +14,7 @@ local mesIcon={
{'setCL',.7,1,.6},
{'line',5,20,15,30,35,10},
},
info=DOGC{40,40,
info=GC.DO{40,40,
{'setCL',.2,.25,.85},
{'fCirc',20,20,15},
{'setCL',1,1,1},
@@ -23,7 +23,7 @@ local mesIcon={
{'fRect',18,11,4,4},
{'fRect',18,17,4,12},
},
broadcast=DOGC{40,40,
broadcast=GC.DO{40,40,
{'setCL',1,1,1},
{'fRect',2,4,36,26,3},
{'fPoly',2,27,2,37,14,25},
@@ -31,7 +31,7 @@ local mesIcon={
{'fRect',6,11,4,4},{'fRect',14,11,19,4},
{'fRect',6,19,4,4},{'fRect',14,19,19,4},
},
warn=DOGC{40,40,
warn=GC.DO{40,40,
{'setCL',.95,.83,.4},
{'fPoly',20.5,1,0,38,40,38},
{'setCL',0,0,0},
@@ -42,7 +42,7 @@ local mesIcon={
{'fRect',18,11,5,16},
{'fRect',18,30,5,5},
},
error=DOGC{40,40,
error=GC.DO{40,40,
{'setCL',.95,.3,.3},
{'fCirc',20,20,19},
{'setCL',0,0,0},
@@ -92,7 +92,7 @@ function MES.new(icon,str,time)
startTime=.5,
endTime=.5,
time=time or 3,
canvas=DOGC(L),
canvas=GC.DO(L),
width=w,height=h,
scale=h>400 and 1/math.min(h/400,2.6)or 1
})

View File

@@ -10,7 +10,7 @@ local SCN={
stat={
tar=false, --Swapping target
style=false,--Swapping style
mid=false, --Loading point
changeTime=false, --Loading point
time=false, --Full swap time
draw=false, --Swap draw func
},
@@ -50,7 +50,7 @@ end
function SCN.swapUpdate()
local S=SCN.stat
S.time=S.time-1
if S.time==S.mid then
if S.time==S.changeTime then
SCN.init(S.tar,SCN.cur)
collectgarbage()
--Scene swapped this moment
@@ -103,36 +103,36 @@ function SCN.pop()
end
local swap={
none={1,0,function()end},--swapTime, changeTime, drawFunction
flash={8,1,function()gc.clear(1,1,1)end},
fade={30,15,function(t)
none={duration=1,changeTime=0,draw=function()end},--swapTime, changeTime, drawFunction
flash={duration=8,changeTime=1,draw=function()gc.clear(1,1,1)end},
fade={duration=30,changeTime=15,draw=function(t)
t=t>15 and 2-t/15 or t/15
gc.setColor(0,0,0,t)
gc.rectangle('fill',0,0,SCR.w,SCR.h)
end},
fade_togame={120,20,function(t)
fade_togame={duration=120,changeTime=20,draw=function(t)
t=t>20 and(120-t)/100 or t/20
gc.setColor(0,0,0,t)
gc.rectangle('fill',0,0,SCR.w,SCR.h)
end},
slowFade={180,90,function(t)
slowFade={duration=180,changeTime=90,draw=function(t)
t=t>90 and 2-t/90 or t/90
gc.setColor(0,0,0,t)
gc.rectangle('fill',0,0,SCR.w,SCR.h)
end},
swipeL={30,15,function(t)
swipeL={duration=30,changeTime=15,draw=function(t)
t=t/30
gc.setColor(.1,.1,.1,1-abs(t-.5))
t=t*t*(3-2*t)*2-1
gc.rectangle('fill',t*SCR.w,0,SCR.w,SCR.h)
end},
swipeR={30,15,function(t)
swipeR={duration=30,changeTime=15,draw=function(t)
t=t/30
gc.setColor(.1,.1,.1,1-abs(t-.5))
t=t*t*(2*t-3)*2+1
gc.rectangle('fill',t*SCR.w,0,SCR.w,SCR.h)
end},
swipeD={30,15,function(t)
swipeD={duration=30,changeTime=15,draw=function(t)
t=t/30
gc.setColor(.1,.1,.1,1-abs(t-.5))
t=t*t*(2*t-3)*2+1
@@ -146,8 +146,9 @@ function SCN.swapTo(tar,style)--Parallel scene swapping, cannot back
SCN.swapping=true
local S=SCN.stat
S.tar,S.style=tar,style
local s=swap[style]
S.time,S.mid,S.draw=s[1],s[2],s[3]
S.time=swap[style].duration
S.changeTime=swap[style].changeTime
S.draw=swap[style].draw
end
else
MES.new('warn',"No Scene: "..tar)

View File

@@ -1,5 +1,6 @@
local SFX={
getCount=function()return 0 end,
loadAll=function()error("Cannot load before init!")end,
fieldPlay=NULL,
play=NULL,
fplay=NULL,
@@ -11,7 +12,7 @@ function SFX.init(list)
local Sources={}
local count=#list function SFX.getCount()return count end
local function load(skip)
function SFX.loadAll()
for i=1,count do
local N='media/SFX/'..list[i]..'.ogg'
if love.filesystem.getInfo(N)then
@@ -19,11 +20,7 @@ function SFX.init(list)
else
MES.new('warn',"No SFX file: "..N,.1)
end
if not skip and i~=count then
coroutine.yield()
end
end
SFX.loadOne=nil
function SFX.play(s,vol,pos)
if SETTING.sfx==0 or vol==0 then return end
@@ -86,8 +83,5 @@ function SFX.init(list)
end
end
end
SFX.loadOne=coroutine.wrap(load)
function SFX.loadAll()load(true)end
end
return SFX

View File

@@ -2,6 +2,7 @@ local data=love.data
local STRING={}
local int,format=math.floor,string.format
local find,sub,upper=string.find,string.sub,string.upper
local char,byte=string.char,string.byte
do--function STRING.shiftChar(c)
local shiftMap={
@@ -81,9 +82,40 @@ do--function STRING.urlEncode(s)
end
end
function STRING.vcsEncrypt(text,key)
local keyLen=#key
local result=""
local buffer=""
for i=0,#text-1 do
buffer=buffer..char((byte(text,i+1)-32+byte(key,i%keyLen+1))%95+32)
if #buffer==26 then
result=result..buffer
buffer=""
end
end
return result..buffer
end
function STRING.vcsDecrypt(text,key)
local keyLen=#key
local result=""
local buffer=""
for i=0,#text-1 do
buffer=buffer..char((byte(text,i+1)-32-byte(key,i%keyLen+1))%95+32)
if #buffer==26 then
result=result..buffer
buffer=""
end
end
return result..buffer
end
function STRING.readLine(str)
local p=str:find("\n")
return str:sub(1,p-1),str:sub(p+1)
if p then
return str:sub(1,p-1),str:sub(p+1)
else
return str,""
end
end
function STRING.packBin(s)

View File

@@ -3,7 +3,6 @@ local gc_setColor,gc_setLineWidth=gc.setColor,gc.setLineWidth
local gc_draw,gc_line=gc.draw,gc.line
local gc_rectangle,gc_circle=gc.rectangle,gc.circle
local sin,cos=math.sin,math.cos
local max,min=math.max,math.min
local rnd=math.random
local ins,rem=table.insert,table.remove

View File

@@ -1,3 +1,4 @@
local find=string.find
local next,type=next,type
local TABLE={}
@@ -11,32 +12,41 @@ function TABLE.new(val,count)
end
--Get a copy of [1~#] elements
function TABLE.shift(org)
function TABLE.shift(org,depth)
if not depth then depth=1e99 end
local L={}
for i=1,#org do
if type(org[i])~='table'then
if type(org[i])~='table'or depth==0 then
L[i]=org[i]
else
L[i]=TABLE.shift(org[i])
L[i]=TABLE.shift(org[i],depth-1)
end
end
return L
end
--Get a full copy of a table
function TABLE.copy(org)
--Get a full copy of a table, depth = how many layers will be recreate, default to inf
function TABLE.copy(org,depth)
if not depth then depth=1e99 end
local L={}
for k,v in next,org do
if type(v)~='table'then
if type(v)~='table'or depth==0 then
L[k]=v
else
L[k]=TABLE.copy(v)
L[k]=TABLE.copy(v,depth-1)
end
end
return L
end
--For all things in new if same type in base, push to old
--For all things in new, push to old
function TABLE.cover(new,old)
for k,v in next,new do
old[k]=v
end
end
--For all things in new if same type in old, push to old
function TABLE.update(new,old)
for k,v in next,new do
if type(v)==type(old[k])then
@@ -49,7 +59,7 @@ function TABLE.update(new,old)
end
end
--For all things in new if no val in base, push to old
--For all things in new if no val in old, push to old
function TABLE.complete(new,old)
for k,v in next,new do
if type(v)=='table'then
@@ -96,7 +106,6 @@ end
--Dump a simple lua table
do--function TABLE.dump(L,t)
local find=string.find
local tabs={
[0]="",
"\t",
@@ -151,7 +160,6 @@ end
--Dump a simple lua table (no whitespaces)
do--function TABLE.dumpDeflate(L,t)
local find=string.find
local function dump(L)
local s="return{"
if type(L)~='table'then return end

View File

@@ -1,6 +1,7 @@
local VOC={
getCount=function()return 0 end,
getQueueCount=function()return 0 end,
loadAll=function()error("Cannot load before init!")end,
getFreeChannel=NULL,
play=NULL,
update=NULL,
@@ -17,7 +18,7 @@ function VOC.init(list)
local function loadVoiceFile(N,vocName)
local fileName='media/VOICE/'..SETTING.cv..'/'..vocName..'.ogg'
if love.filesystem.getInfo(fileName)then
bank[vocName]={love.audio.newSource(fileName,'static')}
bank[vocName]={love.audio.newSource(fileName,'stream')}
table.insert(Source[N],vocName)
return true
end
@@ -36,7 +37,7 @@ function VOC.init(list)
return L[n]
--Load voice with string
end
local function load(skip)
function VOC.loadAll()
for i=1,count do
Source[list[i]]={}
@@ -49,11 +50,7 @@ function VOC.init(list)
end
end
if not Source[list[i]][1]then Source[list[i]]=nil end
if not skip and i~=count then
coroutine.yield()
end
end
VOC.loadOne=nil
function VOC.getQueueCount()
return #voiceQueue
@@ -117,8 +114,5 @@ function VOC.init(list)
end
end
end
VOC.loadOne=coroutine.wrap(load)
function VOC.loadAll()load(true)end
end
return VOC

View File

@@ -6,228 +6,16 @@ local host=
local port='10026'
local path='/tech/socket/v1'
local debugMode=''--S:send, R:receive, M=mark
local wsThread=[[
-- lua + LÖVE threading websocket client
-- Original pure lua ver. by flaribbit and Particle_G
-- Threading version by MrZ
local triggerCHN,sendCHN,readCHN,threadName=...
local CHN_demand,CHN_getCount=triggerCHN.demand,triggerCHN.getCount
local CHN_push,CHN_pop=triggerCHN.push,triggerCHN.pop
local SOCK=require'socket'.tcp()
local JSON=require'Zframework.json'
do--Connect
local host=CHN_demand(sendCHN)
local port=CHN_demand(sendCHN)
local path=CHN_demand(sendCHN)
local body=CHN_demand(sendCHN)
local timeout=CHN_demand(sendCHN)
SOCK:settimeout(timeout)
local res,err=SOCK:connect(host,port)
if err then CHN_push(readCHN,err)return end
--WebSocket handshake
if not body then body=''end
SOCK:send(
'GET '..path..' HTTP/1.1\r\n'..
'Host: '..host..':'..port..'\r\n'..
'Connection: Upgrade\r\n'..
'Upgrade: websocket\r\n'..
'Content-Type: application/json\r\n'..
'Content-Length: '..#body..'\r\n'..
'Sec-WebSocket-Version: 13\r\n'..
'Sec-WebSocket-Key: osT3F7mvlojIvf3/8uIsJQ==\r\n\r\n'..--secKey
body
)
--First line of HTTP
res,err=SOCK:receive('*l')
if not res then CHN_push(readCHN,err)return end
local code,ctLen
code=res:find(' ')
code=res:sub(code+1,code+3)
--Get body length from headers and remove headers
repeat
res,err=SOCK:receive('*l')
if not res then CHN_push(readCHN,err)return end
if not ctLen and res:find('length')then
ctLen=tonumber(res:match('%d+'))
end
until res==''
--Result
if ctLen then
if code=='101'then
CHN_push(readCHN,'success')
else
res,err=SOCK:receive(ctLen)
if not res then
CHN_push(readCHN,err)
else
res=JSON.decode(res)
CHN_push(readCHN,(code or"XXX")..":"..(res and res.reason or"Server Error"))
end
return
end
end
SOCK:settimeout(0)
end
local byte=string.byte
local band,shl=bit.band,bit.lshift
local _send do
local char=string.char
local bor,bxor=bit.bor,bit.bxor
local shr=bit.rshift
local mask_key={1,14,5,14}
local mask_str=char(unpack(mask_key))
function _send(op,message)
]]..(debugMode:find'S'and''or'--')..[[print((">> %s[%d]:%s"):format(threadName,#message,message))
--Message type
SOCK:send(char(bor(0x80,op)))
if message then
--Length
local length=#message
if length>65535 then
SOCK:send(char(bor(127,0x80),0,0,0,0,band(shr(length,24),0xff),band(shr(length,16),0xff),band(shr(length,8),0xff),band(length,0xff)))
elseif length>125 then
SOCK:send(char(bor(126,0x80),band(shr(length,8),0xff),band(length,0xff)))
else
SOCK:send(char(bor(length,0x80)))
end
SOCK:send(mask_str)
local msgbyte={byte(message,1,length)}
for i=1,length do
msgbyte[i]=bxor(msgbyte[i],mask_key[(i-1)%4+1])
end
return SOCK:send(char(unpack(msgbyte)))
else
SOCK:send('\128'..mask_str)
return 0
end
end
end
local res,err
local op,fin
local length
local lBuffer=""--Long multi-data buffer
local UFF--Un-finished-frame mode
local sBuffer=""--Short multi-frame buffer
while true do--Running
CHN_demand(triggerCHN)
--Send
while CHN_getCount(sendCHN)>=2 do
local op=CHN_pop(sendCHN)
local message=CHN_pop(sendCHN)
_send(op,message)
end
--Read
while true do
if not UFF then--UNF process
--Byte 0-1
res,err=SOCK:receive(2)
if err then break end
op=band(byte(res,1),0x0f)
fin=band(byte(res,1),0x80)==0x80
--Calculating data length
length=band(byte(res,2),0x7f)
if length==126 then
res=SOCK:receive(2)
length=shl(byte(res,1),8)+byte(res,2)
elseif length==127 then
local b={byte(SOCK:receive(8),1,8)}
length=shl(b[5],24)+shl(b[6],16)+shl(b[7],8)+b[8]
end
if length>0 then
--Receive data
local s,_,p=SOCK:receive(length)
if s then
res=s
elseif p then--UNF head
]]..(debugMode:find'R'and''or'--')..[[print(("<< %s[%d/%d]:%s"):format(threadName,#p,length,#p<50 and p or p:sub(1,50)))
UFF=true
sBuffer=sBuffer..p
length=length-#p
break
end
else
res=""
end
else
local s,e,p=SOCK:receive(length)
if s then
]]..(debugMode:find'R'and''or'--')..[[print(("<< %s(%d):%s"):format(threadName,length,#s<50 and s or s:sub(1,50)))
sBuffer=sBuffer..s
length=length-#s
elseif p then
]]..(debugMode:find'R'and''or'--')..[[print(("<< %s(%d):%s"):format(threadName,length,#p<50 and p or p:sub(1,50)))
sBuffer=sBuffer..p
length=length-#p
end
if length==0 then
res,sBuffer=sBuffer,""
UFF=false
else
break
end
end
]]..(debugMode:find'R'and''or'--')..[[print(("<< %s[(%d)]:%s"):format(threadName,#res,#res<800 and res or res:sub(1,150).."\n...\n"..res:sub(-150)))
--React
if op==8 then--8=close
CHN_push(readCHN,op)
SOCK:close()
if type(res)=='string'then
CHN_push(readCHN,res:sub(3))--Warning: with 2 bytes close code
else
CHN_push(readCHN,"WS Error")
end
elseif op==0 then--0=continue
lBuffer=lBuffer..res
if fin then
]]..(debugMode:find'M'and''or'--')..[[print("FIN=1 (c")
CHN_push(readCHN,lBuffer)
lBuffer=""
else
]]..(debugMode:find'M'and''or'--')..[[print("FIN=0 (c")
end
else
CHN_push(readCHN,op)
if fin then
]]..(debugMode:find'M'and''or'--')..[[print("OP: "..op.."\tFIN=1")
CHN_push(readCHN,res)
else
]]..(debugMode:find'M'and''or'--')..[[print("OP: "..op.."\tFIN=0")
sBuffer=res
]]..(debugMode:find'M'and''or'--')..[[print("START pack: "..res)
end
end
end
end
]]
local type=type
local timer=love.timer.getTime
local CHN=love.thread.newChannel()
local CHN_getCount,CHN_push,CHN_pop=CHN.getCount,CHN.push,CHN.pop
local TRD=love.thread.newThread("\n")
local TRD_isRunning=TRD.isRunning
local WS={}
local wsList=setmetatable({},{
@@ -255,22 +43,25 @@ function WS.switchHost(_1,_2,_3)
end
function WS.connect(name,subPath,body,timeout)
if wsList[name]and wsList[name].thread then
wsList[name].thread:release()
end
local ws={
real=true,
thread=love.thread.newThread(wsThread),
thread=love.thread.newThread('Zframework/websocket_thread.lua'),
triggerCHN=love.thread.newChannel(),
sendCHN=love.thread.newChannel(),
readCHN=love.thread.newChannel(),
lastPingTime=0,
lastPongTime=timer(),
pingInterval=12,
pingInterval=6,
status='connecting',--'connecting', 'running', 'dead'
sendTimer=0,
alertTimer=0,
pongTimer=0,
}
wsList[name]=ws
ws.thread:start(ws.triggerCHN,ws.sendCHN,ws.readCHN,name)
ws.thread:start(ws.triggerCHN,ws.sendCHN,ws.readCHN)
CHN_push(ws.sendCHN,host)
CHN_push(ws.sendCHN,port)
CHN_push(ws.sendCHN,path..subPath)
@@ -295,7 +86,7 @@ end
function WS.alert(name)
local ws=wsList[name]
ws.alertTimer=2
ws.alertTimer=2.6
end
local OPcode={
@@ -333,7 +124,11 @@ function WS.read(name)
local ws=wsList[name]
if ws.real and ws.status~='connecting'and CHN_getCount(ws.readCHN)>=2 then
local op,message=CHN_pop(ws.readCHN),CHN_pop(ws.readCHN)
if op==8 then ws.status='dead'end--8=close
if op==8 then--8=close
ws.status='dead'
elseif op==9 then--9=ping
WS.send(name,message or"",'pong')
end
ws.lastPongTime=timer()
ws.pongTimer=1
return message,OPname[op]or op
@@ -352,36 +147,44 @@ end
function WS.update(dt)
local time=timer()
for name,ws in next,wsList do
if ws.real then
if CHN_getCount(ws.triggerCHN)==0 then
CHN_push(ws.triggerCHN,0)
end
if ws.status=='connecting'then
local mes=CHN_pop(ws.readCHN)
if mes then
if mes=='success'then
ws.status='running'
ws.lastPingTime=time
ws.lastPongTime=time
ws.pongTimer=1
else
ws.status='dead'
MES.new('warn',text.wsFailed..": "..(mes=="timeout"and text.netTimeout or mes))
if ws.real and ws.status~='dead'then
if TRD_isRunning(ws.thread)then
if CHN_getCount(ws.triggerCHN)==0 then
CHN_push(ws.triggerCHN,0)
end
if ws.status=='connecting'then
local mes=CHN_pop(ws.readCHN)
if mes then
if mes=='success'then
ws.status='running'
ws.lastPingTime=time
ws.lastPongTime=time
ws.pongTimer=1
else
ws.status='dead'
MES.new('warn',text.wsFailed..": "..(mes=="timeout"and text.netTimeout or mes))
end
end
elseif ws.status=='running'then
if time-ws.lastPingTime>ws.pingInterval then
WS.send(name,"",'pong')
end
if time-ws.lastPongTime>6+2*ws.pingInterval then
WS.close(name)
end
end
elseif ws.status=='running'then
if time-ws.lastPingTime>ws.pingInterval then
CHN_push(ws.sendCHN,9)
CHN_push(ws.sendCHN,"")--ping
ws.lastPingTime=time
end
if time-ws.lastPongTime>6+2*ws.pingInterval then
WS.close(name)
if ws.sendTimer>0 then ws.sendTimer=ws.sendTimer-dt end
if ws.pongTimer>0 then ws.pongTimer=ws.pongTimer-dt end
if ws.alertTimer>0 then ws.alertTimer=ws.alertTimer-dt end
else
ws.status='dead'
local err=ws.thread:getError()
if err then
err=err:sub((err:find(":",(err:find(":")or 0)+1)or 0)+1,(err:find("\n")or 0)-1)
MES.new('warn',text.wsClose..err)
WS.alert(name)
end
end
if ws.sendTimer>0 then ws.sendTimer=ws.sendTimer-dt end
if ws.pongTimer>0 then ws.pongTimer=ws.pongTimer-dt end
if ws.alertTimer>0 then ws.alertTimer=ws.alertTimer-dt end
end
end
end

View File

@@ -0,0 +1,191 @@
local triggerCHN,sendCHN,readCHN=...
local CHN_demand,CHN_getCount=triggerCHN.demand,triggerCHN.getCount
local CHN_push,CHN_pop=triggerCHN.push,triggerCHN.pop
local SOCK=require'socket'.tcp()
local JSON=require'Zframework.json'
do--Connect
local host=CHN_demand(sendCHN)
local port=CHN_demand(sendCHN)
local path=CHN_demand(sendCHN)
local body=CHN_demand(sendCHN)
local timeout=CHN_demand(sendCHN)
SOCK:settimeout(timeout)
local res,err=SOCK:connect(host,port)
assert(res,err)
--WebSocket handshake
if not body then body=''end
SOCK:send(
'GET '..path..' HTTP/1.1\r\n'..
'Host: '..host..':'..port..'\r\n'..
'Connection: Upgrade\r\n'..
'Upgrade: websocket\r\n'..
'Content-Type: application/json\r\n'..
'Content-Length: '..#body..'\r\n'..
'Sec-WebSocket-Version: 13\r\n'..
'Sec-WebSocket-Key: osT3F7mvlojIvf3/8uIsJQ==\r\n\r\n'..--secKey
body
)
--First line of HTTP
res,err=SOCK:receive('*l')
assert(res,err)
local code,ctLen
code=res:find(' ')
code=res:sub(code+1,code+3)
--Get body length from headers and remove headers
repeat
res,err=SOCK:receive('*l')
assert(res,err)
if not ctLen and res:find('length')then
ctLen=tonumber(res:match('%d+'))
end
until res==''
--Result
if ctLen then
if code=='101'then
CHN_push(readCHN,'success')
else
res,err=SOCK:receive(ctLen)
res=JSON.decode(assert(res,err))
error((code or"XXX")..":"..(res and res.reason or"Server Error"))
end
end
SOCK:settimeout(0)
end
local YIELD=coroutine.yield
local byte,char=string.byte,string.char
local band,bor,bxor=bit.band,bit.bor,bit.bxor
local shl,shr=bit.lshift,bit.rshift
local mask_key={1,14,5,14}
local mask_str=char(unpack(mask_key))
local function _send(op,message)
--Message type
SOCK:send(char(bor(op,0x80)))
if message then
--Length
local length=#message
if length>65535 then
SOCK:send(char(bor(127,0x80),0,0,0,0,band(shr(length,24),0xff),band(shr(length,16),0xff),band(shr(length,8),0xff),band(length,0xff)))
elseif length>125 then
SOCK:send(char(bor(126,0x80),band(shr(length,8),0xff),band(length,0xff)))
else
SOCK:send(char(bor(length,0x80)))
end
local msgbyte={byte(message,1,length)}
for i=1,length do
msgbyte[i]=bxor(msgbyte[i],mask_key[(i-1)%4+1])
end
return SOCK:send(mask_str..char(unpack(msgbyte)))
else
SOCK:send('\128'..mask_str)
return 0
end
end
local sendThread=coroutine.wrap(function()
while true do
while CHN_getCount(sendCHN)>=2 do
_send(CHN_pop(sendCHN),CHN_pop(sendCHN))
end
YIELD()
end
end)
local function _receive(sock,len)
local buffer=""
while true do
local r,e,p=sock:receive(len)
if r then
buffer=buffer..r
len=len-#r
elseif p then
buffer=buffer..p
len=len-#p
elseif e then
return nil,e
end
if len==0 then
return buffer
end
YIELD()
end
end
local readThread=coroutine.wrap(function()
local res,err
local op,fin
local lBuffer=""--Long multi-pack buffer
while true do
--Byte 0-1
res,err=_receive(SOCK,2)
assert(res,err)
op=band(byte(res,1),0x0f)
fin=band(byte(res,1),0x80)==0x80
--Calculating data length
local length=band(byte(res,2),0x7f)
if length==126 then
res,err=_receive(SOCK,2)
assert(res,err)
length=shl(byte(res,1),8)+byte(res,2)
elseif length==127 then
local lenData
lenData,err=_receive(SOCK,8)
assert(res,err)
local _,_,_,_,_5,_6,_7,_8=byte(lenData,1,8)
length=shl(_5,24)+shl(_6,16)+shl(_7,8)+_8
end
res,err=_receive(SOCK,length)
assert(res,err)
--React
if op==8 then--8=close
CHN_push(readCHN,8)--close
if type(res)=='string'then
CHN_push(readCHN,res:sub(3))--Warning: 2 bytes close code at start so :sub(3)
else
CHN_push(readCHN,"WS closed")
end
return
elseif op==0 then--0=continue
lBuffer=lBuffer..res
if fin then
CHN_push(readCHN,lBuffer)
lBuffer=""
end
else
CHN_push(readCHN,op)
if fin then
CHN_push(readCHN,res)
lBuffer=""
else
lBuffer=res
end
end
YIELD()
end
end)
local success,err
while true do--Running
CHN_demand(triggerCHN)
success,err=pcall(sendThread)
if not success or err then break end
success,err=pcall(readThread)
if not success or err then break end
end
SOCK:close()
CHN_push(readCHN,8)--close
CHN_push(readCHN,err or"Disconnected")
error()

View File

@@ -1,18 +1,19 @@
local floatWheel=0
local love=love
local max,min=math.max,math.min
local float=0
return function(y,key1,key2)
if y>0 then
if floatWheel<0 then floatWheel=0 end
floatWheel=floatWheel+y^1.2
float=max(float,0)+y^1.2
elseif y<0 then
if floatWheel>0 then floatWheel=0 end
floatWheel=floatWheel-(-y)^1.2
if float>0 then float=0 end
float=min(float,0)-(-y)^1.2
end
while floatWheel>=1 do
while float>=1 do
love.keypressed(key1 or"up")
floatWheel=floatWheel-1
float=float-1
end
while floatWheel<=-1 do
while float<=-1 do
love.keypressed(key2 or"down")
floatWheel=floatWheel+1
float=float+1
end
end

View File

@@ -16,25 +16,25 @@ local int,ceil,abs=math.floor,math.ceil,math.abs
local max,min=math.max,math.min
local sub,ins,rem=string.sub,table.insert,table.remove
local getFont,setFont,mStr=getFont,setFont,mStr
local mDraw,mDraw_X,mDraw_Y=ADRAW.draw,ADRAW.simpX,ADRAW.simpY
local mDraw,mDraw_X,mDraw_Y=GC.draw,GC.simpX,GC.simpY
local xOy=SCR.xOy
local downArrowIcon=DOGC{40,25,{'fPoly',0,0,20,25,40,0}}
local upArrowIcon=DOGC{40,25,{'fPoly',0,25,20,0,40,25}}
local clearIcon=DOGC{40,40,
local downArrowIcon=GC.DO{40,25,{'fPoly',0,0,20,25,40,0}}
local upArrowIcon=GC.DO{40,25,{'fPoly',0,25,20,0,40,25}}
local clearIcon=GC.DO{40,40,
{'fRect',16,5,8,3},
{'fRect',8,8,24,3},
{'fRect',11,14,18,21},
}
local sureIcon=DOGC{40,40,
local sureIcon=GC.DO{40,40,
{'setFT',35},
{'mText',"?",20,-6},
}
local smallerThen=DOGC{20,20,
local smallerThen=GC.DO{20,20,
{'setLW',5},
{'line',18,2,1,10,18,18},
}
local largerThen=DOGC{20,20,
local largerThen=GC.DO{20,20,
{'setLW',5},
{'line',2,2,19,10,2,18},
}
@@ -166,39 +166,43 @@ function button:draw()
local ATV=self.ATV
local c=self.color
local r,g,b=c[1],c[2],c[3]
gc_setColor(.2+r*.8,.2+g*.8,.2+b*.8,.7)
gc_rectangle('fill',x-ATV,y-ATV,w+2*ATV,h+2*ATV)
--Button
gc_setColor(.15+r*.7,.15+g*.7,.15+b*.7,.9)
gc_rectangle('fill',x-ATV,y-ATV,w+2*ATV,h+2*ATV,3)
if ATV>0 then
gc_setLineWidth(4)
gc_setColor(1,1,1,ATV*.125)
gc_rectangle('line',x-ATV+2,y-ATV+2,w+2*ATV-4,h+2*ATV-4)
gc_setLineWidth(2)
gc_setColor(.97,.97,.975,ATV*.125)
gc_rectangle('line',x-ATV+2,y-ATV+2,w+2*ATV-4,h+2*ATV-4,3)
end
--Object
local obj=self.obj
local y0=y+h*.5-ATV*.5
gc_setColor(1,1,1,.2+ATV*.05)
if self.align=='M'then
local x0=x+w*.5
mDraw(obj,x0-1.5,y0-1.5)
mDraw(obj,x0-1.5,y0+1.5)
mDraw(obj,x0+1.5,y0-1.5)
mDraw(obj,x0+1.5,y0+1.5)
gc_setColor(r*.5,g*.5,b*.5)
mDraw(obj,x0-1,y0-1)
mDraw(obj,x0-1,y0+1)
mDraw(obj,x0+1,y0-1)
mDraw(obj,x0+1,y0+1)
gc_setColor(r*.55,g*.55,b*.55)
mDraw(obj,x0,y0)
elseif self.align=='L'then
local edge=self.edge
mDraw_Y(obj,x+edge-1.5,y0-1.5)
mDraw_Y(obj,x+edge-1.5,y0+1.5)
mDraw_Y(obj,x+edge+1.5,y0-1.5)
mDraw_Y(obj,x+edge+1.5,y0+1.5)
gc_setColor(r*.5,g*.5,b*.5)
mDraw_Y(obj,x+edge-1,y0-1)
mDraw_Y(obj,x+edge-1,y0+1)
mDraw_Y(obj,x+edge+1,y0-1)
mDraw_Y(obj,x+edge+1,y0+1)
gc_setColor(r*.55,g*.55,b*.55)
mDraw_Y(obj,x+edge,y0)
elseif self.align=='R'then
local x0=x+w-self.edge-obj:getWidth()
mDraw_Y(obj,x0-1.5,y0-1.5)
mDraw_Y(obj,x0-1.5,y0+1.5)
mDraw_Y(obj,x0+1.5,y0-1.5)
mDraw_Y(obj,x0+1.5,y0+1.5)
gc_setColor(r*.5,g*.5,b*.5)
mDraw_Y(obj,x0-1,y0-1)
mDraw_Y(obj,x0-1,y0+1)
mDraw_Y(obj,x0+1,y0-1)
mDraw_Y(obj,x0+1,y0+1)
gc_setColor(r*.55,g*.55,b*.55)
mDraw_Y(obj,x0,y0)
end
end
@@ -287,21 +291,38 @@ function key:draw()
local x,y,w,h=self.x,self.y,self.w,self.h
local ATV=self.ATV
local c=self.color
local align=self.align
local r,g,b=c[1],c[2],c[3]
gc_setColor(1,1,1,ATV*.1)
gc_rectangle('fill',x,y,w,h)
--Frame
if not self.noFrame then
gc_setColor(.2+r*.8,.2+g*.8,.2+b*.8,.7)
gc_setLineWidth(2)
gc_rectangle('line',x,y,w,h,3)
end
gc_setColor(.2+r*.8,.2+g*.8,.2+b*.8,.7)
gc_setLineWidth(4)
gc_rectangle('line',x,y,w,h)
--Fill
if self.fShade then
gc_setColor(r,g,b,ATV*.25)
if align=='M'then
mDraw(self.fShade,x+w*.5,y+h*.5)
elseif align=='L'then
mDraw_Y(self.fShade,x+self.edge,y+h*.5)
elseif align=='R'then
mDraw_Y(self.fShade,x+w-self.edge-self.fShade:getWidth(),y+h*.5)
end
else
gc_setColor(1,1,1,ATV*.05)
gc_rectangle('fill',x,y,w,h,3)
end
gc_setColor(r,g,b,1.2)
if self.align=='M'then
--Object
gc_setColor(r,g,b)
if align=='M'then
mDraw(self.obj,x+w*.5,y+h*.5)
elseif self.align=='L'then
elseif align=='L'then
mDraw_Y(self.obj,x+self.edge,y+h*.5)
elseif self.align=='R'then
elseif align=='R'then
mDraw_Y(self.obj,x+w-self.edge-self.obj:getWidth(),y+h*.5)
end
end
@@ -312,7 +333,7 @@ function key:press(_,_,k)
self.code(k)
if self.sound then SFX.play('key')end
end
function WIDGET.newKey(D)--name,x,y,w[,h][,fText][,color][,font=30][,sound=true][,align='M'][,edge=0],code[,hideF][,hide]
function WIDGET.newKey(D)--name,x,y,w[,h][,fText][,fShade][,noFrame][,color][,font=30][,sound=true][,align='M'][,edge=0],code[,hideF][,hide]
if not D.h then D.h=D.w end
local _={
name= D.name or"_",
@@ -331,6 +352,8 @@ function WIDGET.newKey(D)--name,x,y,w[,h][,fText][,color][,font=30][,sound=true]
},
fText= D.fText,
fShade= D.fShade,
noFrame=D.noFrame,
color= D.color and(COLOR[D.color]or D.color)or COLOR.Z,
font= D.font or 30,
sound= D.sound~=false,
@@ -375,22 +398,22 @@ function switch:draw()
local x,y=self.x,self.y-25
local ATV=self.ATV
--Frame
gc_setLineWidth(2)
gc_setColor(1,1,1,.6+ATV*.1)
gc_rectangle('line',x,y,50,50,3)
--Checked
if ATV>0 then
gc_setColor(1,1,1,ATV*.08)
gc_rectangle('fill',x,y,50,50)
gc_setColor(1,1,1,ATV*.06)
gc_rectangle('fill',x,y,50,50,3)
end
if self.CHK>0 then
gc_setColor(.9,1,.9,self.CHK/6)
gc_setLineWidth(6)
gc_setLineWidth(5)
gc_line(x+5,y+25,x+18,y+38,x+45,y+11)
end
--Frame
gc_setLineWidth(4)
gc_setColor(1,1,1,.6+ATV*.05)
gc_rectangle('line',x,y,50,50)
--Drawable
gc_setColor(self.color)
mDraw_Y(self.obj,x-12-ATV-self.obj:getWidth(),y+25)
@@ -501,16 +524,19 @@ function slider:draw()
local cx=x+(x2-x)*self.pos/self.unit
local bx,by,bw,bh=cx-10-ATV*.5,y-16-ATV,20+ATV,32+2*ATV
gc_setColor(.8,.8,.8)
gc_rectangle('fill',bx,by,bw,bh)
gc_rectangle('fill',bx,by,bw,bh,3)
--Glow
if ATV>0 then
gc_setLineWidth(2)
gc_setColor(1,1,1,ATV*.16)
gc_rectangle('line',bx+1,by+1,bw-2,bh-2)
gc_setColor(.97,.97,.975,ATV*.16)
gc_rectangle('line',bx+1,by+1,bw-2,bh-2,3)
end
--Float text
if self.TAT>0 and self.show then
setFont(25)
gc_setColor(1,1,1,self.TAT/180)
gc_setColor(.97,.97,.975,self.TAT/180)
mStr(self:show(),cx,by-30)
end
@@ -537,7 +563,7 @@ function slider:drag(x)
if p~=P then
self.code(P)
end
if self.change and TIME()-self.lastTime>.26 then
if self.change and TIME()-self.lastTime>.5 then
self.lastTime=TIME()
self.change()
end
@@ -657,10 +683,12 @@ function selector:draw()
local w=self.w
local ATV=self.ATV
--Frame
gc_setColor(1,1,1,.6+ATV*.1)
gc_setLineWidth(3)
gc_rectangle('line',x,y,w,60)
gc_setLineWidth(2)
gc_rectangle('line',x,y,w,60,3)
--Arrow
gc_setColor(1,1,1,.2+ATV*.1)
local t=(TIME()%.5)^.5
if self.select>1 then
@@ -681,7 +709,7 @@ function selector:draw()
--Drawable
gc_setColor(self.color)
ADRAW.simpX(self.obj,x+w*.5,y+17-21)
GC.simpX(self.obj,x+w*.5,y+17-21)
gc_setColor(1,1,1)
setFont(30)
mStr(self.selText,x+w*.5,y+43-21)
@@ -815,11 +843,11 @@ function inputBox:draw()
local ATV=self.ATV
gc_setColor(1,1,1,ATV*.08)
gc_rectangle('fill',x,y,w,h)
gc_rectangle('fill',x,y,w,h,3)
gc_setColor(1,1,1)
gc_setLineWidth(3)
gc_rectangle('line',x,y,w,h)
gc_rectangle('line',x,y,w,h,3)
--Drawable
setFont(self.font)
@@ -971,12 +999,12 @@ function textBox:draw()
--Background
gc_setColor(0,0,0,.4)
gc_rectangle('fill',x,y,w,h)
gc_rectangle('fill',x,y,w,h,3)
--Frame
gc_setLineWidth(3)
gc_setLineWidth(2)
gc_setColor(WIDGET.sel==self and COLOR.lN or COLOR.Z)
gc_rectangle('line',x,y,w,h)
gc_rectangle('line',x,y,w,h,3)
--Texts
setFont(self.font)
@@ -987,12 +1015,12 @@ function textBox:draw()
gc_setColor(1,1,1)
if #texts>cap then
local len=h*h/(#texts*lineH)
gc_rectangle('fill',-15,(h-len)*scrollPos/((#texts-cap)*lineH),12,len)
gc_rectangle('fill',-15,(h-len)*scrollPos/((#texts-cap)*lineH),12,len,3)
end
--Clear button
if not self.fix then
gc_rectangle('line',w-40,0,40,40)
gc_rectangle('line',w-40,0,40,40,3)
gc_draw(self.sure==0 and clearIcon or sureIcon,w-40,0)
end
@@ -1144,14 +1172,14 @@ function listBox:draw()
--Frame
gc_setColor(WIDGET.sel==self and COLOR.lN or COLOR.Z)
gc_setLineWidth(3)
gc_rectangle('line',0,0,w,h)
gc_setLineWidth(2)
gc_rectangle('line',0,0,w,h,3)
--Slider
if #list>cap then
gc_setColor(1,1,1)
local len=h*h/(#list*lineH)
gc_rectangle('fill',-15,(h-len)*scrollPos/((#list-cap)*lineH),12,len)
gc_rectangle('fill',-15,(h-len)*scrollPos/((#list-cap)*lineH),12,len,3)
end
--List
@@ -1315,7 +1343,7 @@ function WIDGET.drag(x,y,dx,dy)
local W=WIDGET.sel
if W.drag then
W:drag(x,y+WIDGET.scrollPos,dx,dy)
elseif not W:isAbove(x,y)then
elseif not W:isAbove(x,y+WIDGET.scrollPos)then
WIDGET.unFocus(true)
end
else
@@ -1443,7 +1471,7 @@ local widgetCover do
ins(L,{'fRect',0,i,1,2})
ins(L,{'fRect',0,360-i,1,2})
end
widgetCover=DOGC(L)
widgetCover=GC.DO(L)
end
local scr_w,scr_h
function WIDGET.resize(w,h)

View File

@@ -1,10 +1,9 @@
VERSION={
build=344,
code=1506,
short="V0.15.6",
string="Alpha V0.15.6",
room="V1.0",
name="强化装甲 Reinforced Armor",
build=358,
code=1600,
string="V0.16.0@DEV",
room="V1.1",
name="空间站 Space station",
}
function love.conf(t)
t.identity='Techmino'--Saving folder
@@ -26,7 +25,7 @@ function love.conf(t)
W.resizable=true
W.fullscreen=false
W.vsync=0--Unlimited FPS
W.msaa=false--Num of samples to use with multi-sampled antialiasing
W.msaa=10--Multi-sampled antialiasing
W.depth=0--Bits/samp of depth buffer
W.stencil=1--Bits/samp of stencil buffer
W.display=1--Monitor ID

View File

@@ -33,8 +33,9 @@
irs true 提前旋转
ims true 提前移动
skin [设置] 方块颜色包含25个整数(1~16)的table
face [设置] 方块朝向包含25个整数(0~3)的table
skinSet [设置] 方块贴图,只能填写内置皮肤的名字
skin [设置] 方块颜色包含25个整数(1~16)的table
face [设置] 方块朝向包含25个整数(0~3)的table
block true 是否显示方块
ghost 0.3 影子透明度(0~1)
@@ -75,12 +76,13 @@
fkey1 false 按下功能键1后执行的函数
fkey2 false 按下功能键2后执行的函数
keyCancel {} 包含禁止使用的按键的id例如{1,2}就是禁止左移和右移
fine [设置] 是否开启非极简提示音
fine [设置] 是否开启非极简提示音
fineKill false 是否开启非极简即死
b2bKill false 是否开启断b2b即死
missionKill false 是否开启强制任务
dropPiece NULL 放一块后要执行的函数,输入玩家对象
task NULL 每帧会*继续执行*的函数,输入玩家对象,注意:使用协程技术
noInitSZO false 是否禁止SZO块开局如果禁止开局序列会自动跳过最多连续五个SZO
bg 'none' 背景,只能填写内置背景的名字
bgm 'race' 背景音乐名(或者列表随机,例如{'race','push'}),只能用内置音乐库的音乐名
@@ -129,14 +131,14 @@ return{--返回一个table你也可以在之前定义一些常量或者函数
dropPiece=function(P)if P.stat.row>=40 then P win('finish')end end,
bg='bg2',bgm='race',
},
load=function()--生成玩家
load=function()--模式加载函数,这里只生成了一个玩家,常用的单人模式可以不写,默认使用这个函数
PLY.newPlayer(1)--1是玩家编号默认用户控制1号玩家
end,
mesDisp=function(P)--40行模式需要显示的信息
setFont(55)
local r=40-P.stat.row
if r<0 then r=0 end
mStr(r,69,265)--把计算出来的剩余行数r显示出来
mStr(r,63,265)--把计算出来的剩余行数r显示出来
PLY.draw.drawTargetLine(P,r)--使用自带的境界高度线绘制函数
end,
score=function(P)return{P.stat.time,P.stat.piece}end,--游戏结束时需要保存的本局关键信息

View File

@@ -8,7 +8,7 @@
如果打算自己导入游戏的话需要降噪+裁剪+调整音量后再转为ogg格式 (不支持别的, 因为ogg音质好体积小)
目前游戏内正在使用, 必须录制的音频文件名们:
single, double, triple, techrash
single, double, triple, techrash (读作\'tekrʌʃ\)
以上直接念就可以,用于普通直接消行
mini, b2b, b2b2b
@@ -21,10 +21,11 @@
z-spin single
z-spin double
z-spin triple
z-spin techrash
(z-spin techrash)
(z-spin pentacrash)
(z-spin hexacrash)
对于 S L J T O I 每一个都是这样, 五种语音, 加括号的是消5和消6, 一般不用所以可以不录
对于 S L J T O I 每一个都是这样至少四条语音
加括号一般不用所以可以不录(消5和消6),
对于P, Q, F, E, U, V, W, X, R, Y, N, H
这些方块也可以有上面那些语音,但由于仅在五连块使用还会显著增加语音包体积, 所以不录也可以
@@ -32,7 +33,7 @@
这俩可以直接念也可以略做修改
win, lose, bye
这几个可以自由发挥, 能用在三个场合就行
这几个可以自由发挥, 能用在三个场合就行,尽量不要太长
test, happy, doubt, sad, egg
这几个是特殊音效,具体使用情况不定

200
main.lua
View File

@@ -1,16 +1,16 @@
--[[
______ __ _
/_ __/___ _____ / /_ ____ ___ (_)____ ____
/ / / _ \ / ___// __ \ / __ `__ \ / // __ \ / __ \
/ / / __// /__ / / / // / / / / // // / / // /_/ /
/_/ \___/ \___//_/ /_//_/ /_/ /_//_//_/ /_/ \____/
# ______ __ _ #
# /_ __/___ _____ / /_ ____ ___ (_)____ ____ #
# / / / _ \ / ___// __ \ / __ `__ \ / // __ \ / __ \ #
# / / / __// /__ / / / // / / / / // // / / // /_/ / #
# /_/ \___/ \___//_/ /_//_/ /_/ /_//_//_/ /_/ \____/ #
Techmino is my first "huge project"
optimization is welcomed if you also love tetromino stacking game
Instructions:
1. I made a framework called Zframework, most code in Zframework are not directly relevant to game;
2. "xxx" are texts for reading, 'xxx' are string values just in program;
3. Some goto statement are used for better performance. All goto-labes have detailed names so don't afraid;
1. I made a framework called Zframework, *most* code in Zframework are not directly relevant to game;
2. "xxx" are texts for reading by player, 'xxx' are string values just used in program;
3. Some goto statement are used for better performance. All goto-labes have detailed names so don't be afraid;
4. Except "gcinfo" function of lua itself, other "gc" are short for "graphics";
]]--
@@ -19,7 +19,6 @@
-- setmetatable(_G,{__newindex=function(self,k,v)print('>>'..k)print(debug.traceback():match("\n.-\n\t(.-): "))rawset(self,k,v)end})
--Declaration
goto REM love=require"love"::REM::--Just tell IDE to load love-api, no actual usage
local fs=love.filesystem
TIME=love.timer.getTime
YIELD=coroutine.yield
@@ -28,6 +27,7 @@ MOBILE=SYSTEM=='Android'or SYSTEM=='iOS'
SAVEDIR=fs.getSaveDirectory()
--Global Vars & Settings
FIRSTLAUNCH=false
DAILYLAUNCH=false
--System setting
@@ -78,12 +78,37 @@ NET= require'parts.net'
VK= require'parts.virtualKey'
AIFUNC= require'parts.ai'
AIBUILDER= require'parts.AITemplate'
RSlist= require'parts.RSlist'DSCP=RSlist.TRS.centerPos
PLY= require'parts.player'
netPLY= require'parts.netPlayer'
MODES= require'parts.modes'
--Initialize field[1]
FIELD[1]=DATA.newBoard()
--Load settings and statistics
TABLE.cover(FILE.load('conf/user')or{},USER)
TABLE.cover(FILE.load('conf/unlock')or{},RANKS)
TABLE.update(FILE.load('conf/settings')or{},SETTING)
TABLE.update(FILE.load('conf/data')or{},STAT)
TABLE.cover(FILE.load('conf/key')or{},keyMap)
TABLE.cover(FILE.load('conf/virtualkey')or{},VK_org)
--Initialize fields, sequence, missions, gameEnv for cutsom game
local fieldData=FILE.load('conf/customBoards')
if fieldData then
fieldData=STRING.split(fieldData,"!")
for i=1,#fieldData do
DATA.pasteBoard(fieldData[i],i)
end
else
FIELD[1]=DATA.newBoard()
end
local sequenceData=FILE.load('conf/customSequence')
if sequenceData then DATA.pasteSequence(sequenceData)end
local missionData=FILE.load('conf/customMissions')
if missionData then DATA.pasteMission(missionData)end
local customData=FILE.load('conf/customEnv')
if customData and customData.version==VERSION.code then TABLE.complete(customData,CUSTOMENV)end
TABLE.complete(require"parts.customEnv0",CUSTOMENV)
--First start for phones
if not fs.getInfo('conf/settings')and MOBILE then
@@ -96,62 +121,63 @@ if SETTING.fullscreen then love.window.setFullscreen(true)end
--Initialize image libs
IMG.init{
lock='mess/lock.png',
dialCircle='mess/dialCircle.png',
dialNeedle='mess/dialNeedle.png',
lifeIcon='mess/life.png',
badgeIcon='mess/badge.png',
ctrlSpeedLimit='mess/ctrlSpeedLimit.png',
speedLimit='mess/speedLimit.png',--Not used, for future C2-mode
pay1='mess/pay1.png',
pay2='mess/pay2.png',
lock='media/image/mess/lock.png',
dialCircle='media/image/mess/dialCircle.png',
dialNeedle='media/image/mess/dialNeedle.png',
lifeIcon='media/image/mess/life.png',
badgeIcon='media/image/mess/badge.png',
ctrlSpeedLimit='media/image/mess/ctrlSpeedLimit.png',
speedLimit='media/image/mess/speedLimit.png',--Not used, for future C2-mode
pay1='media/image/mess/pay1.png',
pay2='media/image/mess/pay2.png',
nakiCH='characters/nakiharu.png',
miyaCH='characters/miya.png',
miyaF1='characters/miya_f1.png',
miyaF2='characters/miya_f2.png',
miyaF3='characters/miya_f3.png',
miyaF4='characters/miya_f4.png',
electric='characters/electric.png',
hbm='characters/hbm.png',
miyaCH='media/image/characters/miya.png',
miyaF1='media/image/characters/miya_f1.png',
miyaF2='media/image/characters/miya_f2.png',
miyaF3='media/image/characters/miya_f3.png',
miyaF4='media/image/characters/miya_f4.png',
nakiCH='media/image/characters/nakiharu.png',
xiaoyaCH='media/image/characters/xiaoya.png',
electric='media/image/characters/electric.png',
hbm='media/image/characters/hbm.png',
lanterns={
'lanterns/1.png',
'lanterns/2.png',
'lanterns/3.png',
'lanterns/4.png',
'lanterns/5.png',
'lanterns/6.png',
'media/image/lanterns/1.png',
'media/image/lanterns/2.png',
'media/image/lanterns/3.png',
'media/image/lanterns/4.png',
'media/image/lanterns/5.png',
'media/image/lanterns/6.png',
},
}
SKIN.init{
'crystal_scf',
'matte_mrz',
'contrast_mrz',
'polkadots_scf',
'toy_scf',
'smooth_mrz',
'simple_scf',
'glass_scf',
'penta_scf',
'bubble_scf',
'minoes_scf',
'pure_mrz',
'bright_scf',
'glow_mrz',
'plastic_mrz',
'paper_mrz',
'yinyang_scf',
'cartooncup_earety',
'jelly_miya',
'brick_notypey',
'gem_notypey',
'classic',
'ball_shaw',
'retro_notypey',
'textbone_mrz',
'coloredbone_mrz',
'wtf',
{name="crystal_scf",path='media/image/skin/crystal_scf.png'},
{name="matte_mrz",path='media/image/skin/matte_mrz.png'},
{name="contrast_mrz",path='media/image/skin/contrast_mrz.png'},
{name="polkadots_scf",path='media/image/skin/polkadots_scf.png'},
{name="toy_scf",path='media/image/skin/toy_scf.png'},
{name="smooth_mrz",path='media/image/skin/smooth_mrz.png'},
{name="simple_scf",path='media/image/skin/simple_scf.png'},
{name="glass_scf",path='media/image/skin/glass_scf.png'},
{name="penta_scf",path='media/image/skin/penta_scf.png'},
{name="bubble_scf",path='media/image/skin/bubble_scf.png'},
{name="minoes_scf",path='media/image/skin/minoes_scf.png'},
{name="pure_mrz",path='media/image/skin/pure_mrz.png'},
{name="bright_scf",path='media/image/skin/bright_scf.png'},
{name="glow_mrz",path='media/image/skin/glow_mrz.png'},
{name="plastic_mrz",path='media/image/skin/plastic_mrz.png'},
{name="paper_mrz",path='media/image/skin/paper_mrz.png'},
{name="yinyang_scf",path='media/image/skin/yinyang_scf.png'},
{name="cartooncup_earety",path='media/image/skin/cartooncup_earety.png'},
{name="jelly_miya",path='media/image/skin/jelly_miya.png'},
{name="brick_notypey",path='media/image/skin/brick_notypey.png'},
{name="gem_notypey",path='media/image/skin/gem_notypey.png'},
{name="classic",path='media/image/skin/classic.png'},
{name="ball_shaw",path='media/image/skin/ball_shaw.png'},
{name="retro_notypey",path='media/image/skin/retro_notypey.png'},
{name="textbone_mrz",path='media/image/skin/textbone_mrz.png'},
{name="coloredbone_mrz",path='media/image/skin/coloredbone_mrz.png'},
{name="wtf",path='media/image/skin/wtf.png'},
}
--Initialize sound libs
@@ -170,7 +196,7 @@ BGM.init((function()
local L={}
for _,v in next,fs.getDirectoryItems('media/BGM')do
if fs.getRealDirectory('media/BGM/'..v)~=SAVEDIR then
table.insert(L,v:sub(1,-5))
table.insert(L,{name=v:sub(1,-5),path='media/BGM/'..v})
else
MES.new('warn',"Dangerous file : %SAVE%/media/BGM/"..v)
end
@@ -241,39 +267,54 @@ end
do
local needSave
if not fs.getInfo('conf/data')then
FIRSTLAUNCH=true
needSave=true
end
if type(STAT.version)~='number'then
STAT.version=0
needSave=true
end
if STAT.version<1302 then
if STAT.version<1500 then
FILE.clear_s('')
end
if STAT.version<1405 then
fs.remove('conf/user')
fs.remove('conf/key')
end
if STAT.version<1505 then
fs.remove('record/bigbang.rec')
fs.remove('conf/replay')
end
if STAT.version==1506 then
local temp1,temp2
if fs.getInfo('record/master_l.rec')then temp1=fs.read('record/master_l.rec')end
if fs.getInfo('record/master_u.rec')then temp2=fs.read('record/master_u.rec')end
if temp1 then fs.write('record/master_u.rec',temp1)end
if temp2 then fs.write('record/master_l.rec',temp2)end
RANKS.master_l,RANKS.master_u=RANKS.master_u,RANKS.master_l
if RANKS.tsd_u then RANKS.tsd_u=0 end
needSave=true
end
if STAT.version~=VERSION.code then
STAT.version=VERSION.code
needSave=true
love.event.quit('restart')
end
if SETTING.ghostType=='greyCell'then
SETTING.ghostType='grayCell'
needSave=true
end
if not SETTING.VKSkin then SETTING.VKSkin=1 end
if not TABLE.find({8,10,13,17,22,29,37,47,62,80,100},SETTING.frameMul)then
SETTING.frameMul=100
end
SETTING.appLock=nil
SETTING.dataSaving=nil
if not SETTING.VKSkin then SETTING.VKSkin=1 end
for _,v in next,SETTING.skin do if v<1 or v>17 then v=17 end end
if
SETTING.RS=='ZRS'or SETTING.RS=='BRS'or
SETTING.RS=='ASCplus'or SETTING.RS=='C2sym'
then SETTING.RS='TRS'end
if SETTING.ghostType=='greyCell'then SETTING.ghostType='grayCell'end
if type(SETTING.skinSet)=='number'then SETTING.skinSet='crystal_scf'end
if not TABLE.find({8,10,13,17,22,29,37,47,62,80,100},SETTING.frameMul)then SETTING.frameMul=100 end
for _,v in next,VK_org do v.color=nil end
if RANKS.infinite then RANKS.infinite=0 end
if RANKS.infinite_dig then RANKS.infinite_dig=0 end
if not RANKS.sprint_10l then RANKS.sprint_10l=0 end
if RANKS.master_l then RANKS.master_n,RANKS.master_l=RANKS.master_l needSave=true end
if RANKS.master_u then RANKS.master_h,RANKS.master_u=RANKS.master_u needSave=true end
for k in next,RANKS do
if type(k)=='number'then
RANKS[k]=nil
@@ -295,10 +336,6 @@ do
fs.remove(k..'.rec')
end
end
if not RANKS.sprint_10l then
RANKS.sprint_10l=0
needSave=true
end
if needSave then
FILE.save(SETTING,'conf/settings')
@@ -308,10 +345,7 @@ do
end
--Apply system setting
LANG.set(SETTING.lang)
VK.setShape(SETTING.VKSkin)
applyBlockSatur(SETTING.blockSatur)
applyFieldSatur(SETTING.fieldSatur)
applySettings()
--Load replays
for _,fileName in next,fs.getDirectoryItems('replay')do

BIN
media/BGM/beat5th.ogg Normal file

Binary file not shown.

BIN
media/BGM/here.ogg Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

BIN
media/BGM/shift.ogg Normal file

Binary file not shown.

BIN
media/BGM/there.ogg Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Some files were not shown because too many files have changed in this diff Show More