mirror of
https://github.com/TriM-Organization/Linglun-Converter.git
synced 2024-11-28 16:15:25 +08:00
文档更新,代码更新
This commit is contained in:
parent
7c078be0cf
commit
732dd0453d
55
README.md
55
README.md
@ -3,7 +3,7 @@
|
||||
<h3 align="center">一个免费开源的《我的世界》数字音频转换器</h3>
|
||||
|
||||
<p align="center">
|
||||
<img src="https://forthebadge.com/images/badges/built-with-love.svg">
|
||||
<img src="https://img.shields.io/badge/BUILD%20WITH%20LOVE-FF3432?style=for-the-badge">
|
||||
<p>
|
||||
|
||||
|
||||
@ -15,65 +15,42 @@
|
||||
[![][release]](../../releases)
|
||||
|
||||
|
||||
简体中文 | [English](README_EN.md)
|
||||
<!-- 简体中文 | [English](README_EN.md) -->
|
||||
|
||||
|
||||
## 软件介绍🚀
|
||||
|
||||
伶伦 是一款免费开源的 **《我的世界》** 数字音频工作站
|
||||
**伶伦** 是一款免费开源的 **《我的世界》** 数字音频工作站
|
||||
|
||||
伶伦转换器 是仅用于 **《我的世界》** 数字音频转换的工具
|
||||
**伶伦转换器** 是仅用于 **《我的世界》** 数字音频转换的工具
|
||||
|
||||
欢迎加群:[861684859](https://jq.qq.com/?_wv=1027&k=hpeRxrYr)
|
||||
|
||||
## 软件架构🏢
|
||||
## 教程📕
|
||||
|
||||
暂无
|
||||
[转换器的使用与安装](./docs/功能使用说明.md)
|
||||
|
||||
## 使用教程📕
|
||||
[对于小白的答疑指南](./docs/新手答疑指南.md)
|
||||
|
||||
暂无
|
||||
[对于本软件部分疑问的一些解答](./docs/问与答.md)
|
||||
|
||||
### 安装教程
|
||||
暂无
|
||||
[生成文件的使用](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%9A%84%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md)
|
||||
|
||||
[转换库的代码文档](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E5%BA%93%E7%9A%84%E7%94%9F%E6%88%90%E4%B8%8E%E5%8A%9F%E8%83%BD%E6%96%87%E6%A1%A3.md)
|
||||
|
||||
[转换乐器对照参考表](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E8%BD%AC%E6%8D%A2%E4%B9%90%E5%99%A8%E5%AF%B9%E7%85%A7%E8%A1%A8.md)
|
||||
|
||||
## 致谢列表🙏
|
||||
|
||||
> 感谢广大群友为此程序提供的测试等支持
|
||||
> 感谢广大群友为此库提供的测试和建议等
|
||||
>
|
||||
> 若您对我们有所贡献但您的名字没有显示在此列表中,请联系我!
|
||||
> 若您对我们有所贡献但您的名字没有出现在此列表中,请联系我们!
|
||||
|
||||
## 联系我们📞
|
||||
|
||||
QQ群 [861684859](https://jq.qq.com/?_wv=1027&k=hpeRxrYr)
|
||||
|
||||
## 待办事项⏲
|
||||
|
||||
* - [ ] 支持自动安装
|
||||
* - [ ] 支持多语言
|
||||
* - [ ] 支持音乐编辑
|
||||
* - [ ] 窗口优化
|
||||
* - [ ] 1.支持插件功能
|
||||
* - [ ] 2.进度条
|
||||
* - [ ] 3.可以将音乐写入音符盒(红乐)
|
||||
* - [ ] 4.修改UI界面使之适应当前功能
|
||||
* - [ ] 5.支持自动给音符盒绑定更多的音色
|
||||
* - [ ] 6.可以由.schematic文件导入地图,亦可反向处理
|
||||
* - [ ] 7.制作软件下载器使用户更直观地操作
|
||||
* - [ ] 8.支持自定义创建websocket服务器播放音乐
|
||||
* - [ ] 9.支持使用红石播放音乐
|
||||
* - [ ] 10.支持采用延时的播放器
|
||||
* - [ ] 11.支持使用bdx导出结构
|
||||
* - [ ] 12.支持采用tp的方法播放
|
||||
* - [ ] 13.支持识别曲谱(简谱)图片解析音乐
|
||||
* - [ ] 14.支持使用瀑布流的方式播放音乐
|
||||
* - [ ] 15.支持读入Everyone Piano的曲谱文件(.eop)
|
||||
* - [ ] 16.支持读入Musescore的通用曲谱文件,即musicXML(.mscz、.mscx)
|
||||
* - [ ] 17.支持自动搜寻地图目录位置(网易&微软)
|
||||
* - [ ] 18.支持读入JPword曲谱文件(.jpd)
|
||||
* - [ ] 19.新的UI设计,以及UI主题文件
|
||||
* - [ ] 20.以小节为单位做音符播放时间对标
|
||||
|
||||
电邮 [TriM-Organization@hotmail.com](mailto:TriM-Organization@hotmail.com)
|
||||
|
||||
|
||||
[Bilibili: 凌云金羿]: https://img.shields.io/badge/Bilibili-%E5%87%8C%E4%BA%91%E9%87%91%E7%BE%BF-00A1E7?style=for-the-badge
|
||||
|
@ -46,7 +46,7 @@
|
||||
那么请把看到的如左下图的界面变为右下图吧:
|
||||
|
||||
<table><tr>
|
||||
<td><img src="https://foruda.gitee.com/images/1665933104313107707/41108f03_9911226.jpeg"> </td>
|
||||
<td><img src="https://foruda.gitee.com/images/1665933104313107707/41108f03_9911226.jpeg"></td>
|
||||
<td><img src="https://foruda.gitee.com/images/1665933122534781330/3887a901_9911226.jpeg"></td>
|
||||
</tr></table>
|
||||
|
||||
|
@ -5,40 +5,44 @@
|
||||
## 下载与启动教程
|
||||
|
||||
### [视窗(Windows)操作系统](./download%26start/Windows.md)
|
||||
### [里纽克斯(Linux)与其衍生操作系统](./download%26start/Linux.md)
|
||||
### [林纳克斯(Linux)与其衍生操作系统](./download%26start/Linux.md)
|
||||
### [安卓(Android)与其衍生操作系统](./download%26start/Android.md)
|
||||
|
||||
## 使用教程
|
||||
|
||||
1. 参数说明
|
||||
|
||||
<img src=https://foruda.gitee.com/images/1674146209644269990/26b53aa7_9911226.png>
|
||||
<img src=https://foruda.gitee.com/images/1695492228675012042/2136cbe4_9911226.png>
|
||||
|
||||
- midi路径:含有mid文件路径、文件名、后缀的完整文件路径,或者一个目录(magicDemo可接受批量转换)。可以使用相对或绝对路径皆可
|
||||
- MIDI地址:含有mid文件路径、文件名、后缀的完整文件路径,或者一个目录(可接受批量转换)。相对或绝对路径皆可
|
||||
|
||||
- 输出路径:输出文件夹的路径,不需要指示文件名
|
||||
- 输出地址:输出文件夹的路径,不需要指示文件名
|
||||
|
||||
- 转换算法:通过不同通道隔离音轨,识别最佳乐器的算法编号为3(金羿的算法);将所有的音轨合并,通过通道来分组的算法编号为2(神羽和金羿的算法);旧算法,即通过音轨分组的算法编号为1(Dislink的算法)。新算法在某些方面转换效果更好,但是如果新算法转换有误的话,请使用旧算法。
|
||||
- 转换算法(**已废弃**):通过不同通道隔离音轨,识别最佳乐器的算法编号为3(金羿的算法);将所有的音轨合并,通过通道来分组的算法编号为2(神羽和金羿的算法);旧算法,即通过音轨分组的算法编号为1(Dislink的算法)。新算法在某些方面转换效果更好,但是如果新算法转换有误的话,请使用旧算法。
|
||||
|
||||
- 输出格式:目前的演示程序仅支持`BDX`结构和`MCPACK`包
|
||||
- 输出文件类型:支持 `BDX` 结构和 `MCPACK` 包,其中,以 `BDX` 结构输出支持延迟和积分两种播放器, `MCPACK` 附加包则比前者多了一种 中继器播放器。
|
||||
|
||||
- 播放方式:目前的转换库仅支持**计分板**和**延迟**的两种播放方式,具体地关于这些播放方式如何使用的问题,详见[生成文件的使用说明](./%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%9A%84%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md)
|
||||
- 播放器类型:`BDX` 结构仅支持**计分板**和**延迟**的两种播放方式;`MCPACK`则支持**计分板**、**延迟**和**中继器**三种播放方式。具体地关于这些播放方式如何使用的问题,详见[生成文件的使用说明](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%9A%84%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md)
|
||||
|
||||
- 音量:小数数据,在0~1(包含首尾)的范围之内,用以表示播放音量大小。
|
||||
- 音量大小:正小数,在0(不含)~1(包含)的范围之内,用以表示播放音量大小。
|
||||
|
||||
- 速度倍率:小数数据,其值不可为0,用以表示游戏中播放此音乐的速度倍数。
|
||||
- 速度倍率:正小数,其值不可为0,用以表示游戏中播放此音乐的速度倍数。
|
||||
|
||||
- 进度条:是否启用进度条。目前的转换库已经支持自定义进度条,但是当前的演示程序并不能做到这一点。具体的有关进度条自定义的内容,可以看[功能文档](./%E5%BA%93%E7%9A%84%E7%94%9F%E6%88%90%E4%B8%8E%E5%8A%9F%E8%83%BD%E6%96%87%E6%A1%A3.md#%E8%BF%9B%E5%BA%A6%E6%9D%A1%E8%87%AA%E5%AE%9A%E4%B9%89)中的相关部分自行修改参数。
|
||||
- 进度条:是否启用自动生成进度条。
|
||||
|
||||
- 计分板名称(仅计分板播放器):游戏内的计分板名称
|
||||
- 若是,则可选是否自定义进度条
|
||||
|
||||
自定义的进度条样式,可以参考[功能文档](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E5%BA%93%E7%9A%84%E7%94%9F%E6%88%90%E4%B8%8E%E5%8A%9F%E8%83%BD%E6%96%87%E6%A1%A3.md#%E8%BF%9B%E5%BA%A6%E6%9D%A1%E8%87%AA%E5%AE%9A%E4%B9%89)
|
||||
|
||||
- 计分板名称(仅计分板播放器):游戏内的用以延迟的计分板名称
|
||||
|
||||
- 是否重置计分板(仅计分板播放器):歌曲放完是否重置,推荐选择自动重置
|
||||
|
||||
- 玩家选择器(仅延迟播放器):包括 `@x` 在内的全部选择器。例:若要选择全部标签为`Holo`的玩家,则需要如此输入:`@a[tag=Holo]`
|
||||
|
||||
- 作者(仅BDX结构):音乐结构的生成作者
|
||||
- 作者(仅BDX结构):结构的生成作者署名
|
||||
|
||||
- 指令结构最大高度(仅结构输出):生成音乐结构的最大堆叠高度,可以查看相关[结构部分的开发文档](./%E5%BA%93%E7%9A%84%E7%94%9F%E6%88%90%E4%B8%8E%E5%8A%9F%E8%83%BD%E6%96%87%E6%A1%A3.md#%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%BB%93%E6%9E%84##%E6%96%87%E4%BB%B6%E6%A0%BC%E5%BC%8F)了解详细知识。
|
||||
- 指令结构最大高度(`MCPACK`的计分板播放器不含此项):生成音乐结构的最大堆叠高度。对于如何堆叠的问题,可以查看[结构部分的开发文档](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E5%BA%93%E7%9A%84%E7%94%9F%E6%88%90%E4%B8%8E%E5%8A%9F%E8%83%BD%E6%96%87%E6%A1%A3.md#%E6%96%87%E4%BB%B6%E6%A0%BC%E5%BC%8F)了解详细内容。
|
||||
|
||||
- 没有报错且在输出路径下找到对应的文件即为生成成功:
|
||||
|
||||
|
@ -1,24 +1,24 @@
|
||||
<h1 align="center">伶伦转换器</h1>
|
||||
<h1 align="center">**伶伦转换器**</h1>
|
||||
|
||||
# 新手答疑指南
|
||||
|
||||
**考虑到某些用户电脑技术不是特别先进,且对这个项目充满了好奇心,但是又了解的不是很充分,为此,我特别在这里写一份新手指南,以满足各位的好奇心。放心,本文件全程中文。**
|
||||
|
||||
## 第一部分 关于音·创的作用
|
||||
## 第一部分 关于 **音·创** 的作用
|
||||
|
||||
### 1.1 音·创简介
|
||||
### 1.1 **音·创** 简介
|
||||
|
||||
音·创 Musicreater 是一款免费开源的针对 **《我的世界》** 的midi音乐转换库
|
||||
**音·创 _Musicreater_** 是一款免费开源的针对 **《我的世界》** 的midi音乐转换库
|
||||
|
||||
而能够与人交互,以达到转换功能的,是 音·创 的程序实现:伶伦转换器。
|
||||
而能够与人交互,以达到转换功能的,是 **音·创** 库的程序实现:**伶伦转换器**。
|
||||
|
||||
伶伦转换器 目前已经具备较为完善的[**教程**](./%E5%8A%9F%E8%83%BD%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md),其中包括了下载安装一类,使你能够方便地进行转换。
|
||||
**伶伦转换器** 目前已经具备较为完善的[**教程**](./%E5%8A%9F%E8%83%BD%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md),其中包括了下载安装一类,使你能够方便地进行转换。
|
||||
|
||||
伶伦转换器也是免费开源的,采用**带有特殊条款的Apache2.0**开源协议授权,详情请见[协议](../LICENSE.md)。
|
||||
**伶伦转换器**也是免费开源的,采用**带有特殊条款的Apache2.0**开源协议授权,详情请见[协议](../LICENSE.md)。
|
||||
|
||||
另外的,伶伦转换器并不是伶伦的主要开发方向,其功能也并非是伶伦本体(伶伦DAW)所提供的主要功能。**从音·创到伶伦的开发,其目的是为了方便《我的世界》的音乐作者,进行《我的世界》相关音乐的开发与创作**,而并不是转换MIDI文件!音·创的实现是在伶伦DAW之前试行一定的技术探索,以更好地开发数字音乐工作站。
|
||||
另外的,**伶伦转换器**并不是伶伦的主要开发方向,其功能也并非是 **伶伦** 本体(伶伦DAW)所提供的主要功能。**从 _音·创_ 到 _伶伦_ 的开发,其目的是为了方便 _《我的世界》_ 的音乐作者,进行 _《我的世界》_ 相关音乐的开发与创作**,而并不是转换MIDI文件!转换器的实现是在数字音频工作站的开发之前进行一定的技术探索,以更好地开发数字音乐工作站。
|
||||
|
||||
### 1.2 音·创库版本到底目前有什么功能?
|
||||
### 1.2 **音·创** 库到底有什么功能?
|
||||
* - [x] 支持导入`.mid`文件
|
||||
* - [x] 支持写入`.mcpack`文件
|
||||
* - [x] 支持写入`.bdx`文件
|
||||
@ -59,7 +59,7 @@
|
||||
|
||||
0. 最简单的方法是向你心仪的作编曲人投递一份申请,请求TA将其作编曲过程中的相关工程文件给你,这样,你就可以获得一首乐曲的电子曲谱,从而获得其MIDI文件。
|
||||
1. 如果无法向作曲人申请相关文件的话,成为一个作编曲人也许是一个不错的选择,当然,很多人做不到这一点,但是有必要提到这一点,当你在下面的渠道中都无法获得想要的文件时,你应该考虑是不是需要自己创作内容,或者,请别人帮你创作内容。
|
||||
2. 当你没有这样的文件时,问问别人或者从群里下载公开的文件也是个思路,不过这个办法通常使用次数有限且能找到的文件不多,不过,值得注意的是,**[音·创开发交流群](https://jq.qq.com/?_wv=1027&k=hpeRxrYr)的群文件中所含的MIDI文件均为网友分享学习交流使用,请在下载后一个小时内删除。**
|
||||
2. 当你没有这样的文件时,问问别人或者从群里下载公开的文件也是个思路,不过这个办法通常使用次数有限且能找到的文件不多,不过,值得注意的是,[**音·创**开发交流群](https://jq.qq.com/?_wv=1027&k=hpeRxrYr)的**群文件中所含的MIDI文件均为网友分享学习交流使用,请在下载后一个小时内删除。**
|
||||
3. 自己找MIDI:现在,我将给你提供一个完整的找mid的方法,请认真学习:
|
||||
|
||||
**1.** 首先你需要在[MidiShow](www.midishow.com)网站中注册一个账号,并不复杂,你可能只需要一个QQ号便可以授权登录。
|
||||
@ -125,7 +125,7 @@
|
||||
|
||||
如果你是使用桌面平台游玩基岩版,像我一样,是可以直接打开这个文件、并将这个包导入我的世界的。当然,移动平台也很简单,在游戏资源包界面有导入本地资源包的选项,便可将其导入。
|
||||
|
||||
资源包导入世界之后的使用方法,我们也制作了[**简单的教程**](./%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%9A%84%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md),如果你对使用导入后的文件有所疑问,可以看看。
|
||||
资源包导入世界之后的使用方法,我们也制作了[**简单的教程**](https://gitee.com/TriM-Organization/Musicreater/blob/master/docs/%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%9A%84%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md),如果你对使用导入后的文件有所疑问,可以看看。
|
||||
|
||||
#### 2.4.2 .bdx是什么
|
||||
|
||||
|
@ -1,40 +0,0 @@
|
||||
<h1 align="center">伶伦转换器</h1>
|
||||
|
||||
# 生成文件的使用
|
||||
|
||||
*这是本库所生成文件的使用声明,不是使用教程,点击[此处查看使用教程](%E5%8A%9F%E8%83%BD%E4%BD%BF%E7%94%A8%E8%AF%B4%E6%98%8E.md);若要查看有关文件结构的内容,可以点击[此处](./%E7%94%9F%E6%88%90%E6%96%87%E4%BB%B6%E7%BB%93%E6%9E%84%E8%AF%B4%E6%98%8E.md)*
|
||||
|
||||
## 附加包格式
|
||||
|
||||
支持的文件后缀:`.MCPACK`
|
||||
|
||||
1. 导入附加包
|
||||
2. 在一个循环方块中输入指令 `function index`
|
||||
3. 将需要聆听音乐的实体的播放所用计分板设置为 `1`
|
||||
4. 激活循环方块
|
||||
5. 若想要暂停播放,可以停止循环指令方块的激活状态
|
||||
6. 若想要重置某实体的播放,可以将其播放用的计分板重置
|
||||
|
||||
> 其中 步骤三 和 步骤四 的顺序可以调换。
|
||||
|
||||
## 结构格式
|
||||
|
||||
支持的文件后缀:`.MCSTRUCTURE`、`.BDX`
|
||||
|
||||
1. 将结构导入世界
|
||||
|
||||
- 延迟播放器
|
||||
|
||||
2. 将结构生成的第一个指令方块之模式更改为**脉冲**
|
||||
3. 激活脉冲方块
|
||||
4. 若欲重置播放,可以停止对此链的激活,例如停止区块加载
|
||||
5. 此播放器不支持暂停
|
||||
|
||||
- 计分板播放器
|
||||
|
||||
2. 在所生成的第一个指令方块前,放置一个循环指令方块,其朝向应当对着所生成的第一个方块
|
||||
3. 在循环指令方块中输入使播放对象的播放用计分板加分的指令,延迟为`0`,每次循环增加`1`分
|
||||
4. 激活循环方块
|
||||
5. 若想要暂停播放,可以停止循环指令方块的激活状态
|
||||
6. 若想要重置某实体的播放,可以将其播放用的计分板重置
|
||||
|
16
docs/问与答.md
16
docs/问与答.md
@ -4,19 +4,19 @@
|
||||
|
||||
## 关于音·创与伶伦转换器
|
||||
|
||||
1. “伶伦”是什么?
|
||||
1. “**伶伦**”是什么?
|
||||
|
||||
伶伦是一个针对《我的世界》的数字音频工作站,用以创作、编辑《我的世界》风格的曲目。
|
||||
**伶伦** 是一个针对《我的世界》的数字音频工作站,用以创作、编辑《我的世界》风格的曲目。
|
||||
|
||||
2. “伶伦转换器”是什么?
|
||||
2. “**伶伦转换器**”是什么?
|
||||
|
||||
伶伦转换器是一个用于将Midi文件转换至我的世界可读格式的工具。其使用音·创库作为转换工具库,其目的旨在方便midi创作者进行简单的音乐转换,同时也是音·创库的一个项目实现。
|
||||
**伶伦转换器** 是一个用于将Midi文件转换至我的世界可读格式的工具。其使用 **音·创** 作为转换工具库,其目的旨在方便midi创作者进行简单的音乐转换,同时也是 **音·创** 的一个实现。
|
||||
|
||||
3. 为什么要将音·创库的功能迁移至伶伦转换器?
|
||||
3. 为什么要将 **音·创** 的功能迁移至 **伶伦转换器**?
|
||||
|
||||
音·创库作为单独存在的转换工具库,如果每次更新都需要从源码下载更新可能对用户十分的不友好。而且,音·创库的实现本是为了其他程序的调用,而不是一个转换程序。经过一段时间的观察与开发后,我们发现如果是以一种“可以用来转换音乐”的工具出现在大众面前,那么音·创库不仅不能被人理解,反而可能会让人困惑于其的具体功用,因此将伶伦转换器作为音·创库的实现,将独立的转换功能用更加亲用户的形式展现在大众面前,是一个更好的选择。
|
||||
**音·创** 作为单独存在的转换工具库,如果每次更新都需要从源码下载更新可能对用户十分的不友好。而且,**音·创** 的实现本是为了其他程序的调用,而不是一个转换程序。经过一段时间的观察与开发后,我们发现如果是以一种“可以用来转换音乐”的工具出现在大众面前,那么 **音·创** 不仅不能被人理解,反而可能会让人困惑于其的具体功用,因此将 **伶伦转换器** 作为 **音·创** 库的实现,将独立的转换功能用更加亲用户的形式展现在大众面前,是一个更好的选择。
|
||||
|
||||
4. 之前使用的“音·创库版本”的示例程序,现在还能用吗?
|
||||
4. 之前使用的“**音·创库版本**”的示例程序,现在还能用吗?
|
||||
|
||||
仍然可以使用,不过由于不再维护,已有的错误不会自动修复。
|
||||
|
||||
@ -30,6 +30,6 @@
|
||||
|
||||
详见问1,切换你所需要的播放器即可。
|
||||
|
||||
4. 转换算法是什么?怎么填?是越新越好吗?
|
||||
4. **(_已废弃_)** 转换算法是什么?怎么填?是越新越好吗?
|
||||
|
||||
转换算法是音·创库中所需要指定的内容,转换的算法都已经开源,可以在音·创仓库内找到。目前转换算法1对应的算法是将midi文件中的所有音轨单独提取并逐轨解析。而算法2是将所有音符单独提取出来,而后解析各个音符。算法的转换过程的差异可能会导致结果不同,但由于算法1已经不在进行主动维护,算法2的效果将会比1更好,所以建议使用算法2。算法3所对应的是尚在研究的插值算法,使用可能导致转换出错。
|
228
llc_cli.py
228
llc_cli.py
@ -14,7 +14,7 @@ Copyright © 2023 EillesWan & TriM Org.
|
||||
Terms & Conditions: ./Lisense.md
|
||||
"""
|
||||
|
||||
__version__ = "0.0.5"
|
||||
__version__ = "0.0.6"
|
||||
|
||||
import datetime
|
||||
import os
|
||||
@ -24,15 +24,16 @@ import sys
|
||||
import Musicreater
|
||||
from Musicreater.plugin import ConvertConfig
|
||||
from Musicreater.plugin.bdxfile import to_BDX_file_in_delay, to_BDX_file_in_score
|
||||
from Musicreater.plugin.funcpack import to_function_addon_in_score
|
||||
from Musicreater.plugin.mcstructpack import to_mcstructure_addon_in_delay, to_mcstructure_addon_in_redstone_cd
|
||||
from Musicreater.plugin.addonpack import (
|
||||
to_addon_pack_in_delay,
|
||||
to_addon_pack_in_repeater,
|
||||
to_addon_pack_in_score,
|
||||
)
|
||||
from Musicreater.constants import DEFAULT_PROGRESSBAR_STYLE
|
||||
|
||||
# from Musicreater.plugin.mcstructure import commands_to_structure, commands_to_redstone_delay_structure
|
||||
|
||||
from utils.io import *
|
||||
from languages.lang import languages
|
||||
|
||||
print("小贴:不妨试试Mid-BDX转换网页:在线的多功能Midi转换器")
|
||||
print("https://dislink.github.io/midi2bdx/")
|
||||
|
||||
MainConsole.print(
|
||||
"[#121110 on #F0F2F4] ",
|
||||
@ -44,36 +45,25 @@ osc.project_name = "伶伦转换器"
|
||||
osc.version = __version__
|
||||
|
||||
|
||||
def go_for_args(
|
||||
languageChange: str = "ZH-CN", debugMode: str = "False", logfile: str = "True"
|
||||
):
|
||||
global currentLang
|
||||
if len(sys.argv) > 0:
|
||||
|
||||
def go_for_args(debugMode: str = "False", logfile: str = "True"):
|
||||
global logger
|
||||
currentLang = (
|
||||
languageChange.upper()
|
||||
if languageChange.upper() in languages.keys()
|
||||
else "ZH-CN"
|
||||
)
|
||||
osc.isRelease = False if debugMode.lower() in ("true", "1") else True
|
||||
logger.printing = not osc.isRelease
|
||||
logger.writing = True if logfile.lower() in ("true", "1") else False
|
||||
|
||||
|
||||
if len(sys.argv) > 0:
|
||||
go_for_args(*sys.argv)
|
||||
|
||||
|
||||
def _(__):
|
||||
"""
|
||||
`languages`
|
||||
"""
|
||||
return languages[currentLang][__]
|
||||
|
||||
|
||||
# 显示大标题
|
||||
MainConsole.rule(title="[bold #AB70FF]欢迎使用伶伦独立转换器", characters="=", style="#26E2FF")
|
||||
MainConsole.rule(title="[bold #AB70FF]Welcome to Linglun Converter", characters="-")
|
||||
MainConsole.rule(title="[#AB70FF]版本{} | 音·创内核版本{}".format(__version__,Musicreater.__version__), characters="=", style="#26E2FF")
|
||||
# MainConsole.rule(title="[bold #AB70FF]Welcome to Linglun Converter", characters="-")
|
||||
MainConsole.rule(
|
||||
title="[#AB70FF]版本{} | 音·创内核版本{}".format(__version__, Musicreater.__version__),
|
||||
characters="-",
|
||||
style="#26E2FF",
|
||||
)
|
||||
|
||||
nowYang = datetime.datetime.now()
|
||||
|
||||
@ -99,13 +89,13 @@ else:
|
||||
justify="center",
|
||||
)
|
||||
|
||||
prt(f"{_('LangChd')}{_(':')}{_(currentLang)}")
|
||||
# prt(f"{_('LangChd')}{_(':')}{_(currentLang)}")
|
||||
|
||||
|
||||
def format_ipt(
|
||||
notice: str,
|
||||
fun,
|
||||
err_note: str = f"{_('ErrEnter')}{_(',')}{_('Re-Enter')}{_('.')}",
|
||||
err_note: str = "输入内容有误,请重新输入。",
|
||||
*extraArg,
|
||||
):
|
||||
"""循环输入,以某种格式
|
||||
@ -126,84 +116,81 @@ def format_ipt(
|
||||
|
||||
# 获取midi列表
|
||||
while True:
|
||||
midi_path = ipt(f"{_('ChoosePath')}{_(':')}").lower()
|
||||
midi_path = ipt(f"请键入MIDI地址或所在目录地址:")
|
||||
try:
|
||||
if os.path.exists(midi_path):
|
||||
if os.path.isfile(midi_path):
|
||||
midis = (midi_path,)
|
||||
elif os.path.isdir(midi_path):
|
||||
midis = tuple(
|
||||
(
|
||||
midis = (
|
||||
os.path.join(midi_path, i)
|
||||
for i in os.listdir(midi_path)
|
||||
if i.lower().endswith(".mid") or i.lower().endswith(".midi")
|
||||
)
|
||||
)
|
||||
else:
|
||||
prt(f"{_('ErrEnter')}{_(',')}{_('Re-Enter')}{_('.')}")
|
||||
prt("输入内容有误,请重新输入。")
|
||||
continue
|
||||
else:
|
||||
prt(f"{_('FileNotFound')}{_(',')}{_('Re-Enter')}{_('.')}")
|
||||
prt("该地址不存在,或无法访问该地址,请重新输入。")
|
||||
continue
|
||||
except PermissionError:
|
||||
prt("无法访问该地址,请检查是否给予程序相关文件的访问权限。")
|
||||
continue
|
||||
break
|
||||
|
||||
# 获取输出地址
|
||||
out_path = format_ipt(
|
||||
f"{_('ChooseOutPath')}{_(':')}",
|
||||
os.path.exists,
|
||||
f"{_('FileNotFound')}{_(',')}{_('Re-Enter')}{_('.')}",
|
||||
)[0].lower()
|
||||
while True:
|
||||
out_path = ipt(f"请键入文件生成输出地址:")
|
||||
try:
|
||||
if not os.path.exists(out_path):
|
||||
prt("该地址不存在,或无法访问该地址,请重新输入。")
|
||||
continue
|
||||
except PermissionError:
|
||||
prt("无法访问该地址,请检查是否给予程序相关文件的访问权限。")
|
||||
continue
|
||||
break
|
||||
|
||||
|
||||
# 选择输出格式
|
||||
|
||||
|
||||
def is_in_bdx_mcpack(sth: str):
|
||||
if sth.lower() in ("0", "mcpack"):
|
||||
return 0
|
||||
|
||||
elif sth.lower() in ("1", "bdx"):
|
||||
return 1
|
||||
|
||||
else:
|
||||
raise ValueError("文件格式字符串啊?")
|
||||
|
||||
|
||||
fileFormat = format_ipt(
|
||||
f"{_('ChooseFileFormat')}{_(':')}",
|
||||
is_in_bdx_mcpack,
|
||||
f"{_('ErrEnter')}{_(',')}{_('Re-Enter')}{_('.')}",
|
||||
)[1]
|
||||
return isin(sth, {1: ("bdx", "1", "币帝查", "币帝·艾克斯"), 0: ("mcpack", "0", "唉姆西·派克")})
|
||||
|
||||
|
||||
def is_in_player(sth: str):
|
||||
if sth.lower() in ("0", "延迟", "delay"):
|
||||
return 0
|
||||
elif sth.lower() in ("1", "计分板", "scoreboard"):
|
||||
return 1
|
||||
elif sth.lower() in ('2', "红石", 'redstone'):
|
||||
return 2
|
||||
else:
|
||||
raise ValueError("播放器字符串啊?")
|
||||
return isin(
|
||||
sth,
|
||||
{
|
||||
0: ("delay", "0", "延迟", "帝蕾"),
|
||||
1: ("score", "1", "计分板", "积分", "积分板", "计分", "斯阔尔"),
|
||||
2: ("repeater", "2", "中继器", "瑞皮特"),
|
||||
},
|
||||
)
|
||||
|
||||
|
||||
playerFormat = format_ipt(
|
||||
f"{_('ChoosePlayer')}{_(':')}",
|
||||
is_in_player,
|
||||
f"{_('ErrEnter')}{_(',')}{_('Re-Enter')}{_('.')}",
|
||||
output_file_format = format_ipt(
|
||||
"请键入输出文件类型 (mcpack/0|bdx/1)",
|
||||
is_in_bdx_mcpack,
|
||||
"输入内容有误,请重新输入。",
|
||||
)[1]
|
||||
|
||||
if output_file_format == 0:
|
||||
player_format = format_ipt(
|
||||
"请选择播放器类型 (延迟/0|计分板/1|中继器/2)",
|
||||
is_in_player,
|
||||
"输入内容有误,请重新输入。",
|
||||
)[1]
|
||||
else:
|
||||
player_format = format_ipt(
|
||||
"请选择播放器类型 (延迟/0|计分板/1)",
|
||||
is_in_player,
|
||||
"输入内容有误,请重新输入。",
|
||||
)[1]
|
||||
|
||||
# 真假字符串判断
|
||||
def bool_str(sth: str) -> bool:
|
||||
try:
|
||||
return bool(int(sth))
|
||||
except ValueError:
|
||||
if str(sth).lower() in ("true", "真", "是"):
|
||||
return True
|
||||
elif str(sth).lower() == ("false", "假", "否", "非"):
|
||||
return False
|
||||
else:
|
||||
raise ValueError("布尔字符串啊?")
|
||||
old_exe_enabled = format_ipt(
|
||||
"启用1.19以前的旧版execute指令格式 (否/0|是/1):", bool_str, "输入内容格式错误,应为 是/1/真/t/y 或 否/0/假/f/n"
|
||||
)[1]
|
||||
|
||||
|
||||
if os.path.exists("./demo_config.json"):
|
||||
@ -217,76 +204,95 @@ else:
|
||||
# 提示语 检测函数 错误提示语
|
||||
for args in [
|
||||
(
|
||||
f'{_("EnterVolume")}{_(":")}',
|
||||
float,
|
||||
"音量大小 (0,1]:",
|
||||
float_str,
|
||||
),
|
||||
(
|
||||
f'{_("EnterSpeed")}{_(":")}',
|
||||
float,
|
||||
"速度倍率 (0,+∞):",
|
||||
float_str,
|
||||
),
|
||||
(
|
||||
f'{_("WhetherPgb")}{_(":")}',
|
||||
"自动生成进度条 (否/0|是/1):",
|
||||
bool_str,
|
||||
),
|
||||
(
|
||||
f'{_("EnterSbName")}{_(":")}',
|
||||
"计分板名称:",
|
||||
str,
|
||||
)
|
||||
if playerFormat == 1
|
||||
if player_format == 1
|
||||
else (
|
||||
f'{_("EnterSelecter")}{_(":")}',
|
||||
"受播放玩家的选择器:",
|
||||
str,
|
||||
),
|
||||
(
|
||||
f'{_("WhetherSbReset")}{_(":")}',
|
||||
"自动重置计分板 (否/0|是/1):",
|
||||
bool_str,
|
||||
)
|
||||
if playerFormat == 1
|
||||
if player_format == 1
|
||||
else (),
|
||||
(
|
||||
f'{_("EnterAuthor")}{_(":")}',
|
||||
"BDX作者署名:",
|
||||
str,
|
||||
)
|
||||
if fileFormat == 1
|
||||
if output_file_format == 1
|
||||
else (),
|
||||
(
|
||||
f'{_("EnterMaxHeight")}{_(":")}',
|
||||
"结构生成最大高度 (0,+∞):",
|
||||
int,
|
||||
)
|
||||
if playerFormat == 0
|
||||
if player_format == 0
|
||||
else (),
|
||||
]:
|
||||
if args:
|
||||
prompts.append(format_ipt(*args)[1])
|
||||
prompts.append(
|
||||
format_ipt(*args, err_note="输入内容格式错误,应符合 {}".format(args[1]))[1]
|
||||
)
|
||||
|
||||
if prompts[2]:
|
||||
costom_pgb_enabled = format_ipt(
|
||||
"自定义进度条样式 (否/0|是/1):", bool_str, "输入内容格式错误,应为 是/1/真/t/y 或 否/0/假/f/n"
|
||||
)[1]
|
||||
if costom_pgb_enabled:
|
||||
style = ipt("基本样式组 (回车默认):")
|
||||
if not style:
|
||||
style = DEFAULT_PROGRESSBAR_STYLE[0]
|
||||
yet_part = ipt("未播放样式 (回车默认):")
|
||||
if not yet_part:
|
||||
yet_part = DEFAULT_PROGRESSBAR_STYLE[1][1]
|
||||
done_part = ipt("已播放样式 (回车默认):")
|
||||
if not done_part:
|
||||
done_part = DEFAULT_PROGRESSBAR_STYLE[1][0]
|
||||
|
||||
if playerFormat == 1:
|
||||
cvt_method = to_function_addon_in_score
|
||||
elif playerFormat == 0:
|
||||
cvt_method = to_mcstructure_addon_in_delay
|
||||
elif playerFormat == 2:
|
||||
cvt_method = to_mcstructure_addon_in_redstone_cd
|
||||
if player_format == 1:
|
||||
cvt_method = to_addon_pack_in_score
|
||||
elif player_format == 0:
|
||||
cvt_method = to_addon_pack_in_delay
|
||||
elif player_format == 2:
|
||||
cvt_method = to_addon_pack_in_repeater
|
||||
|
||||
|
||||
for singleMidi in midis:
|
||||
prt("\n" f"{_('Dealing')} {singleMidi} {_(':')}")
|
||||
cvt_mid = Musicreater.MidiConvert.from_midi_file(singleMidi, old_exe_format=False)
|
||||
cvt_cfg = ConvertConfig(out_path, *prompts[:3])
|
||||
prt("\n" f"正在处理 {singleMidi}")
|
||||
cvt_mid = Musicreater.MidiConvert.from_midi_file(
|
||||
singleMidi, old_exe_format=old_exe_enabled
|
||||
)
|
||||
cvt_cfg = ConvertConfig(out_path, *prompts[:2], progressbar=((style, (done_part, yet_part)) if costom_pgb_enabled else True) if prompts[2] else False) # type: ignore
|
||||
|
||||
conversion_result = ((
|
||||
cvt_method(cvt_mid, cvt_cfg, *prompts[3:])
|
||||
)if fileFormat == 0
|
||||
conversion_result = (
|
||||
(cvt_method(cvt_mid, cvt_cfg, *prompts[3:])) # type: ignore
|
||||
if output_file_format == 0
|
||||
else (
|
||||
to_BDX_file_in_score(cvt_mid, cvt_cfg, *prompts[3:])
|
||||
if playerFormat == 1
|
||||
if player_format == 1
|
||||
else to_BDX_file_in_delay(cvt_mid, cvt_cfg, *prompts[3:])
|
||||
))
|
||||
|
||||
prt(
|
||||
f" {_('CmdLength')}{_(':')}{conversion_result[0]}{_(',')}{_('MaxDelay')}{_(':')}{conversion_result[1]}{f'''{_(',')}{_('PlaceSize')}{_(':')}{conversion_result[2]}{_(',')}{_('LastPos')}{_(':')}{conversion_result[3]}''' if fileFormat == 1 else ''}"
|
||||
)
|
||||
)
|
||||
|
||||
exitSth = ipt(_("PressEnterExit")).lower()
|
||||
prt(
|
||||
f" 指令总长:{conversion_result[0]},播放刻数:{conversion_result[1]}{f''',结构大小:{conversion_result[2]},末点坐标:{conversion_result[3]}''' if output_file_format == 1 else ''}" # type: ignore
|
||||
)
|
||||
|
||||
exitSth = ipt("结束。换行以退出程序。")
|
||||
if exitSth == "record":
|
||||
import json
|
||||
|
||||
|
36
utils/io.py
36
utils/io.py
@ -178,3 +178,39 @@ def format_ipt(
|
||||
prt(err_note)
|
||||
continue
|
||||
return result, fun_result
|
||||
|
||||
def isin(sth: str, range_list: dict):
|
||||
sth = sth.lower()
|
||||
for bool_value, res_list in range_list.items():
|
||||
if sth in res_list:
|
||||
return bool_value
|
||||
raise ValueError
|
||||
|
||||
|
||||
# 真假字符串判断
|
||||
def bool_str(sth: str):
|
||||
try:
|
||||
return bool(float(sth))
|
||||
except:
|
||||
if str(sth).lower() in ("true", "真", "是", 'y', 't'):
|
||||
return True
|
||||
elif str(sth).lower() in ("false", "假", "否", 'f', 'n'):
|
||||
return False
|
||||
else:
|
||||
raise ValueError
|
||||
|
||||
|
||||
def float_str(sth: str):
|
||||
try:
|
||||
return float(sth)
|
||||
except ValueError:
|
||||
try:
|
||||
return float(sth.replace("壹", "1").replace("贰", "2").replace("叁", "3").replace("肆", "4").replace("伍", "5").replace("陆", "6").replace("柒", "7").replace("捌", "8").replace("玖", "9").replace("零", "0").replace("一", "1").replace("二",'2').replace("三", "3").replace("四", "4").replace("五", "5").replace("六", "6").replace("七", "7").replace("八", "8").replace("九", "9").replace("〇", "0").replace("洞", "0").replace("幺", "1").replace("俩", "2").replace("两", "2").replace("拐","7").replace("点",'.'))
|
||||
except:
|
||||
raise ValueError
|
||||
|
||||
def int_str(sth: str):
|
||||
try:
|
||||
return int(float_str(sth))
|
||||
except ValueError:
|
||||
raise ValueError
|
Loading…
Reference in New Issue
Block a user