Minecraftをひらがな化する

漢字やカタカナが読めない子供でもMinecraftで遊べるようにUIを平仮名化しました。
平仮名勉強中の子供でも文字に興味を持ってくれるかなと思います。
リモートワークでの業務効率化に貢献すること間違いなしです。
対象は`Minecraft Java Edition`です。

- **2020/07/04追記**
 
     Minecraft Java Edition 1.16.1(ネザーアップデート)でも動作することを確認しました。
    リソースパックを指定しただけではひらがなにならない場合の対応手順を追記しました。 

# 概要

Minecraftのリソースパックという仕組みを利用して実現しています。
バニラ範囲の文字が概ね平仮名になります。
Minecraft本体に付属するリソースファイルをひらがなに変換しリソースパックを作成します。
リソースファイルの再配布にあたるかもしれずライセンス的に問題があるかもしれないので、リソースパックを作るツールとして実現しています。
生成されたリソースパックの取り扱いは自己責任でお願いします。

# 環境

- ツール実行環境 (`Docker`と`Minecraft`が必要です。)

  - Minecraft Java Edition

  - Windows Subsystem for Linux(Ubuntu 18.04)
      - Docker version 18.09.7, build 2d0083d

  - Windows 10 Pro バージョン 2004
      - Docker Desktop Community 2.2.0.5

  - macOS
      - Docker Desktop Community 2.3.0.1

- ツールの`Docker Image`内の環境
  - CentOS 7.7.1908
  - mecab 0.996
  - mecab-ipadic-NEologd
  - python 3.6
      - MeCab 0.996.2
      - jaconv 0.2

# TL;DR

- リソースパックを使うとこのようになります。

    UIはひらがな化されます。
    ![2020-05-03-00-04-26.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/b6c7ad22-8a5a-679f-fb6a-3022fa3cbb6a.png)

    一部ひらがな化できていないものもあります。（右上のメッセージ）
    ![2020-05-03-00-07-28.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/3d51c879-7182-492a-46cf-b4cac9bee7af.png)

- ツールのソース,Docker Imageは下記リポジトリにUPしています。
  (github packagesへのアクセスのためにdocker loginが必要です。 [GitHub Packagesで利用するために Docker を設定する - Githubヘルプ](https://help.github.com/ja/packages/using-github-packages-with-your-projects-ecosystem/configuring-docker-for-use-with-github-packages))

     [リポジトリはこちら](https://github.com/n-noguchi/mc-hiragana-resourcepack-builder)

# 使い方

## 本ツールの使い方

ツールはDockerより起動します。
(github packagesへのアクセスのためにdocker loginが必要です。 [GitHub Packagesで利用するために Docker を設定する - Githubヘルプ](https://help.github.com/ja/packages/using-github-packages-with-your-projects-ecosystem/configuring-docker-for-use-with-github-packages))

**コマンド**

**Windowsでの実行:**

```bash
# windowsのユーザー名は [username] としています。
# 使用するときは環境に合わせて置き換えてください。
docker run -v /c/Users/[username]/AppData/Roaming/.minecraft/assets:/assets:ro -v /c/Users/[username]/AppData/Roaming/.minecraft/resourcepacks:/resourcepacks:rw -e "MINECRAFT_VERSION=1.12" docker.pkg.github.com/n-noguchi/mc-hiragana-resourcepack-builder/mc-hiragana-resourcepack-builder:1.0.0
```

**Windows Subsystem for Linux (Ubuntu 18.04)での実行:**

```bash
# windowsのユーザー名は [username] としています。
# 使用するときは環境に合わせて置き換えてください。
docker run -v /mnt/c/Users/[username]/AppData/Roaming/.minecraft/assets:/assets:ro \
-v /mnt/c/Users/[username]/AppData/Roaming/.minecraft/resourcepacks:/resourcepacks:rw \
-e "MINECRAFT_VERSION=1.12" docker.pkg.github.com/n-noguchi/mc-hiragana-resourcepack-builder/mc-hiragana-resourcepack-builder:1.0.0
```

**macOSでの実行:**

```bash
# macOSのユーザー名は [username] としています。
# 使用するときは環境に合わせて置き換えてください。
docker run -v "/Users/[username]/Library/Application Support/minecraft/assets:/assets:ro" \
-v "/Users/[username]/Library/Application Support/minecraft/resourcepacks:/resourcepacks:rw" \
-e "MINECRAFT_VERSION=1.12" docker.pkg.github.com/n-noguchi/mc-hiragana-resourcepack-builder/mc-hiragana-resourcepack-builder:1.0.0
```

**引数**

|タイプ|名前|説明|
|---|---|---|
|環境変数|`MINECRAFT_VERSION`|`Minecraft Java Edition`のバージョンを指定します。<br>一度起動し、ダウンロードされている必要があります。<br>指定可能なバージョンは`1.12`,`1.13`,`1.14`,`1.15`,`1.16`の何れかです。|
|ボリューム|`/assets`|`Minecraft Java Edition`の`assets`フォルダをマウントします。|
|ボリューム|`/resourcepacks`|`Minecraft Java Edition`の`resourcepacks`フォルダをマウントします。<br>|

**出力**

正常に完了すると、`resourcepacks`フォルダにリソースパックが出力されます。

## リソースパックの使い方

`Minecraft Java Edition`の`resourcepacks`フォルダにリソースパックを配置して、Minecraftを起動します。
その後、Minecraft内からリソースパックを指定します。
リソースパックのフォルダはデフォルトでは以下です。

**`resourcepacks`フォルダ**

|OS|Path|
|---|---|
|Windows|c:/Users/[username]/AppData/Roaming/.minecraft/resourcepacks|
|macOS|/Users/[username]/Library/Application Support/minecraft/resourcepacks|

`resourcepacks`のフォルダに出来上がったリソースパックを配置します。
![2020-05-04-20-55-03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/da8355b1-cc67-edb7-7f40-7a284bd08bad.png)

`Option`を押します。
![2020-05-04-20-56-37.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/03fd639d-3600-bfdb-343d-cf31c43b9f6e.png)

`Resource Packs`を押します。
![2020-05-04-20-57-00.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/f23fbe90-ba0a-a637-8ca5-2c8108648062.png)

該当リソースパックのアイコンを押します。
![2020-05-04-20-57-27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/5bca7053-7e80-669f-ac45-64cc0ae4a744.png)

`Done`を押します。
![2020-05-04-20-57-51.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/87dc6896-bca9-22ae-4cab-36074b7b1936.png)

`かんりょう`を押します。既に平仮名で表示されています。(`hi_jp`という言語を追加しています。)
![](2020-05-04-20-59-01.png)
![2020-05-04-20-59-01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/99cf6444-e2d4-62bc-6fab-fb2d88c403db.png)

TOP画面も平仮名表示になりました。
![](2020-05-04-20-59-23.png)
![2020-05-04-20-59-23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/f0558bac-9f56-27a3-6f0b-aff2857d6f5b.png)

**※リソースパックを選択するだけでは、ひらがなにならない場合もあります。その場合は以下の手順を行います。**

「言語設定」を開きます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/a939aa97-fae3-9d4b-0e88-e06308ba8192.png)

言語「にほんご(ひらがな)(JP)」を選択するとひらがなになります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/79cbbac4-df87-f3b6-e859-a162da74eab8.png)

# 細かい話

## どうやって実現できるか？

UIの文字列を差し替える方法には、リソースパックを使う方法があります。
日本語のリソースはMinecraftに同梱されているはず。
なのでそれをひらがなに翻訳し、リソースパック化すればよいと考えました。

## Minecraftのリソースパックはどうやって作るのか？

まずは、作りたいリソースパックについて確認です。
リソースパックの作り方は、Minecraft公式のwikiに書いてある通りです。
下記をzipファイルにまとめたものです。

**リソースパックに含むもの**

- pack.mcmeta: リソースパックについてのメタ情報を格納するJSONファイル
- pack.png: リソースパックのアイコン。省略可能
- 各種リソースファイル： pack.mcmetaに記載したリソースのファイル

参考 [Tutorials/Creating a resource pack - Official Minecraft Wiki](https://minecraft.gamepedia.com/Tutorials/Creating_a_resource_pack)


`pack.mcmeta`に記載するリソースパックのフォーマット`pack_format`は、Minecraftのバージョンと対応しており、古い場合は警告が出ます。

**`pack_format`と`Minecraft Version`の対応**

|pack_format|Minecraft Version|
|---|---|
|1| Java Edition 1.6 - Java Edition 1.8|
|2| Java Edition 1.9 and Java Edition 1.10|
|3| Java Edition 1.11 and Java Edition 1.12|
|4| Java Edition 1.13 and Java Edition 1.14|
|5| Java Edition 1.15 and Java Edition 1.16|

## Minecraftに同梱されているリソースはどこにあるのか？

`Minecraft Java Edition`では、デフォルトでは以下のフォルダにリソースが格納されます。

|OS|Path|
|---|---|
|macOS|`/Users/[macのユーザー名]/Library/Application Support/minecraft/assets`|
|Windows|`C:\Users\[Windowsのユーザー名]\AppData\Roaming\.minecraft\assets`|

assetsフォルダ配下は以下のような構成です。<br>
複数バージョンをインストールしている場合、indexes配下のファイルは別となりますが、objects配下のデータは混在して管理されています。<br>
gitのような効率的な管理です。<br>

**assets配下のフォルダ構成**

- assets/
   - indexes/
     - [Minecraftのバージョン].json
       リソース名と、ハッシュコード、サイズで構成されるJSONファイル

       ```json
       {
        "objects": {
            "icons/icon_16x16.png": {
                "hash": "bdf48ef6b5d0d23bbb02e17d04865216179f510a",
                "size": 3665
            },
            "icons/icon_32x32.png": {
                "hash": "92750c5f93c312ba9ab413d546f32190c56d6f1f",
                "size": 5362
            },
            ～略～
            "minecraft/lang/ja_jp.json": {
                "hash": "2a0ae8e6a984ab749fce1d6218f165f2b5d31c60",
                "size": 445279
            },
            ～略～
         }
       }
       ```
   - objects/

     - [リソースのハッシュコード先頭２桁]/
       `icons/icon_16x16.png`での例: `bd`

         - [ハッシュコードのファイル]

           `icons/icon_16x16.png`での例:  `bdf48ef6b5d0d23bbb02e17d04865216179f510a`

           ![2020-05-03-10-51-13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/265837/9cfeb7b3-b87d-a195-d885-532217e2367c.png)

参考 : [Tutorials/Sound directory - Official Minecraft Wiki](https://minecraft.gamepedia.com/Tutorials/Sound_directory)

## Minecraftの言語リソースファイルはどのような形式になっているのか。

リソースのフォーマットはタイプごとに異なります。<br>
言語ファイルは以下のような形式になります。`1.12`と`1.13`以降で形式が異なり、結構はまりました。<br>

|Minecraftバージョン|言語リソース名(indexes/[バージョン].json記載)|言語リソースのフォーマット|
|---|---|---|
|1.12|minecraft/lang/ja_jp.lang|リソースのキー＝リソースの文字列|
|1.13以降|minecraft/lang/ja_jp.json|リソースのキーとその文字列のJSON|

**Minecraft Java Edition 1.12のリソース**

```json:assets/indexes/1.12.json
"minecraft/lang/ja_jp.lang": {"hash": "8eedb38dbb5220be3d5aafc2135beb105548f5e1", "size": 192067},
```

```txt:assets/objects/8e/8eedb38dbb5220be3d5aafc2135beb105548f5e1
addServer.add=完了
addServer.enterIp=サーバーアドレス
addServer.enterName=サーバー名
addServer.hideAddress=アドレスを隠す
```

**Minecraft Java Edition 1.15のリソース**

```json:assets/indexes/1.15.json
"minecraft/lang/ja_jp.json": {"hash": "2a0ae8e6a984ab749fce1d6218f165f2b5d31c60", "size": 445279},
```

```json:assets/objects/2a/2a0ae8e6a984ab749fce1d6218f165f2b5d31c60
{
    "addServer.add": "\u5b8c\u4e86",
    "addServer.enterIp": "\u30b5\u30fc\u30d0\u30fc\u30a2\u30c9\u30ec\u30b9",
    "addServer.enterName": "\u30b5\u30fc\u30d0\u30fc\u540d",
    "addServer.hideAddress": "\u30a2\u30c9\u30ec\u30b9\u3092\u96a0\u3059",
```

## 日本語リソース（漢字かな交じりの文字）を平仮名に変換する

リソースパックの作り方、Minecraftのリソースがどう格納されているのかはわかりました。
次はこれを平仮名に変換する方法を検討します。

単純な文字の置き換えでは音読み訓読みや、文脈による読み方の違いに対応できません。
意味を汲み取って読みを取得したいので`mecab`を利用します。
また、正しい読みを取得するために辞書は充実していたほうがよいので`mecab-ipadic-NEologd`を利用します。

### mecab-ipadic-NEologd環境の作り方

mecab+meacb-ipadic-NEologd環境の作り方はほぼ `mecab-ipadic-NEologd`のREADME通りです。

README：[Neologism dictionary based on the language resources on the Web for mecab-ipadic - github.com](https://github.com/neologd/mecab-ipadic-neologd)

今回はツールの配布を簡単にするようDockerで実装します。
READMEの手順だと一部対話型の部分があります。以下のように`-y`をつけると強制yesでインストールできます。

```Dockerfile
RUN cd /mecab/mecab-ipadic-neologd && \
  ./bin/install-mecab-ipadic-neologd -y -n && \
  echo `mecab-config --dicdir`"/mecab-ipadic-neologd"
```

参考：[install-mecab-ipadic-neologd](https://github.com/neologd/mecab-ipadic-neologd/blob/master/bin/install-mecab-ipadic-neologd#L163)

```bash
'-y'|'--forceyes' )
    IS_FORCE_YES=1
    shift 1
    ;;
```

最終的にこのような[Dockerfile](https://github.com/n-noguchi/mc-hiragana-resourcepack-builder/blob/master/Dockerfile)になりました。

### mecabで読みを取得する

`-Oyomi`を指定することで読みを取得できます。

[MeCab: Yet Another Part-of-Speech and Morphological Analyzer #出力フォーマットの変更](https://taku910.github.io/mecab/#format)

`mecab-ipadic-NEologd`のサンプルで読みを取得してみます。
ほぼ期待した結果です。
あとはカタカナから平仮名への単純な置き換えだけです。

```bash
$ NEOLOGD=`mecab-config --dicdir`"/mecab-ipadic-neologd"
$ echo "8月3日に放送された「中居正広の金曜日の スマイルたちへ」(TBS系)で、1日たった5分でぽっこりおなかを解消するというダイエット方法を紹介。キンタロー。のダイエットにも密着。" | mecab -d $NEOLOGD
8月3日  名詞,固有名詞,一般,*,*,*,8月3日,ハチガツミッカ,ハチガツミッカ
に      助詞,格助詞,一般,*,*,*,に,ニ,ニ
放送    名詞,サ変接続,*,*,*,*,放送,ホウソウ,ホーソー
さ      動詞,自立,*,*,サ変・スル,未然レル接続,する,サ,サ
れ      動詞,接尾,*,*,一段,連用形,れる,レ,レ
た      助動詞,*,*,*,特殊・タ,基本形,た,タ,タ
「      記号,括弧開,*,*,*,*,「,「,「
中居正広の金曜日のスマイルたちへ        名詞,固有名詞,一般,*,*,*,中居正広の金曜日のスマイルたちへ,ナカイマサヒロノキンヨウビノスマイルタチヘ,ナカイマサヒロノキンヨービノスマイル
タチヘ
」(     記号,一般,*,*,*,*,*
TBS     名詞,固有名詞,一般,*,*,*,TBS,ティービーエス,ティービーエス
系      名詞,接尾,一般,*,*,*,系,ケイ,ケイ
)       記号,一般,*,*,*,*,*
で      助動詞,*,*,*,特殊・ダ,連用形,だ,デ,デ
、      記号,読点,*,*,*,*,、,、,、
1日     名詞,固有名詞,一般,*,*,*,1日,ツイタチ,ツイタチ
たった  副詞,助詞類接続,*,*,*,*,たった,タッタ,タッタ
5分     名詞,固有名詞,一般,*,*,*,5分,ゴフン,ゴフン
で      助詞,格助詞,一般,*,*,*,で,デ,デ
ぽっこりおなか  名詞,固有名詞,一般,*,*,*,ぽっこりおなか,ポッコリオナカ,ポッコリオナカ
を      助詞,格助詞,一般,*,*,*,を,ヲ,ヲ
解消    名詞,サ変接続,*,*,*,*,解消,カイショウ,カイショー
する    動詞,自立,*,*,サ変・スル,基本形,する,スル,スル
という  助詞,格助詞,連語,*,*,*,という,トイウ,トユウ
ダイエット方法  名詞,固有名詞,一般,*,*,*,ダイエット方法,ダイエットホウホウ,ダイエットホウホー
を      助詞,格助詞,一般,*,*,*,を,ヲ,ヲ
紹介    名詞,サ変接続,*,*,*,*,紹介,ショウカイ,ショーカイ
。      記号,句点,*,*,*,*,。,。,。
キンタロー。    名詞,固有名詞,一般,*,*,*,キンタロー。,キンタロー,キンタロー
の      助詞,連体化,*,*,*,*,の,ノ,ノ
ダイエット      名詞,サ変接続,*,*,*,*,ダイエット,ダイエット,ダイエット
に      助詞,格助詞,一般,*,*,*,に,ニ,ニ
も      助詞,係助詞,*,*,*,*,も,モ,モ
密着    名詞,サ変接続,*,*,*,*,密着,ミッチャク,ミッチャク
。      記号,句点,*,*,*,*,。,。,。
EOS
$ echo "8月3日に放送された「中居正広の金曜日の スマイルたちへ」(TBS系)で、1日たった5分でぽっこりおなかを解消するというダイエット方法を紹介。キンタロー。のダイエットにも密着。" | mecab -d $NEOLOGD -Oyomi
ハチガツミッカニホウソウサレタ「ナカイマサヒロノキンヨウビノスマイルタチヘ」(ティービーエスケイ)デ、ツイタチタッタゴフンデポッコリオナカヲカイショウスルトイウダイエットホウホウヲショウカイ。キンタローノダイエットニモミッチャク。
$
```

## リソースを日本語から平仮名へ変換する

楽なPythonで実現することにしました。

### pythonからmecab呼び出し

pythonの`mecab`パッケージを利用します。

URL：[mecab PyPI](https://pypi.org/project/mecab/)

読みを取得するモード、かつneologdの辞書を利用するので以下のようにオプションを指定します。
辞書のパスは引数から取得します。

```python
mecab_yomi = MeCab.Tagger("-Oyomi -d {0}".format(sys.argv[1]))
```

### カタカナから平仮名への変換

MeCabの読みはカタカナなので平仮名に変換する必要があります。
pythonの`jaconv`パッケージを使います。

URL:[jaconv PyPI](https://pypi.org/project/jaconv/0.2/)

参考：[python 文字列変換【カタカナ⇔ひらがな】](https://qiita.com/mocha_xx/items/07465240d4212d946148)

### リソース内の特殊な文字のあつかい

日本語→カタカナ→平仮名の変換をすると、おかしな文字になるものがありました。
これらを含むリソースは変換対象外としています。

**うまく変換できたもの**

```txt
パンチして木材を回収します -> ぱんちしてもくざいをかいしゅうします

木を探しましょう -> きをさがしましょう

マウスを使って視点移動します -> まうすをつかってしてんいどうします

周りを見渡しましょう -> まわりをみわたしましょう

インベントリを開きましょう -> いんべんとりをひらきましょう

木を倒しましょう -> きをたおしましょう
```

**うまく変換できない：プレースホルダー`%`を持つも文字列**

```txt
%s でジャンプします -> ぱーせんとs でじゃんぷします

%s、%s、%s、%s で移動します -> ぱーせんとs、ぱーせんとs、ぱーせんとs、ぱーせんとs でいどうします

%s を押します -> ぱーせんとs をおします

%s を長押しします -> ぱーせんとs をなげししします

```

最終的に以下のようなスクリプトになりました。

[Minecraft 1.12 用 変換スクリプト](https://github.com/n-noguchi/mc-hiragana-resourcepack-builder/blob/master/ja2hiragana_1.12.py)

[Minecraft 1.13 以降用 変換スクリプト](https://github.com/n-noguchi/mc-hiragana-resourcepack-builder/blob/master/ja2hiragana_ge1.13.py)

# 最後に

たまにおかしい翻訳がありますが、満足のいくものできました。
子供に`村人ゾンビの卵どれ？`とか聞かれることもなくなり、自然と平仮名の勉強もできています。
これでリモートワークの集中力も高くなり一石二鳥です。