Minecraftの地形生成を考える【2】

Minecraftの地形生成を考える【2】

前回、一応基本となる地形生成のパーリンノイズについて一応書きましたので、今回はBeta1.8以降のバイオームわけについて。

バイオーム拡大法
バイオームを拡大していく方法です。
ゆえにMinecraftの地形生成は時間がかかります。

簡単な仕組みは
16×16(チャンク)を生成するために、もっと小さいブロックの四角形(例:4×4)を拡大・補完することで無限の生成を可能にしています。
無限といってもint値やlong値には最大が有るわけですから、その最大のなかのちょっとを何回も拡大することで擬似的に無限世界を生成することができるのです。
一番最初は固定シード値によってランダムに点をばらまくだけです。

拡大・補完の仕方
2×2ならば3×3に拡大します。(n x n => (2n – 1) x (2n – 1))

A B
C D

一番最初の拡大のときは下記のように拡大して補完します

A A or B B
A or C A, B, C or D B or D
C C or D D

この処理の際、シード値を常に座標から計算するなどして一定にしておかないと次のチャンクとの補完結果がずれる場合があります。また隣のチャンクとの差異吸収のために16×16は補完後18×18になるようにしてそこから16×16を取り出すことで次の拡大に影響が出ないようにします。

それ以降の拡大時には大陸や海をちゃんとつなげていくために上下または左右の最頻値をとって補完していきます。
ただし全て異なる場合などは上記同様ランダムに決定していきます
例:

A B
A A

これを、

A A B
A A B
A A A

これをもう一回拡大すると

A A A B B
A A A A B
A A A B B
A A A A A
A A A A A

この拡大処理を十分に繰り返し、あるていどの大きさになったところで終了します。
このようにバイオームのあの複雑なバイオームの境界線を生み出すことができるのです。

Minecraftの地形生成を考える【1】

Minecraftの地形生成を考える【1】
最初はずっと2D世界の話をしていきます。
Minecraftでいうと上からみた世界みたいな感じです。

Minecraftはどこまで行ってもワールドが続きます。
つまり……無限の生成を考えるということである。

有限の生成は実は結構簡単であったりする。
例えば64×64みたいな奴
実装方法としては64×64の世界に、海と陸のブロックをばら撒きランダムで結合したりばらしていったりする。
まあここでは省略しますが。
ランダムが重要になってきます。

しかし無限となると初回で全部ワールドを生成してしまうわけには行きません。
何らかの手段でなめらかに地形を繋げる必要があります。

コレを見てください。Googleでy=2xのグラフです。

この画像の範囲外を想像することはできますか?きっと容易だと思います。
なぜなら数式が与えられている=関数が与えられているからです。
ずっと同じ角度で直線が続いていきます。

もう一つ、プログラム上での乱数は擬似乱数。つまり関数です。
つまり、この疑似乱数を使っている時点で次にくる値が明らかだということ。

javaデフォルトのランダムで同じシード値を与えて初期化すれば、実行するたびに同じ値が出力されるはずです。

Minecraft Beta1.7、使われてるのがパーリンノイズ。同じシード値を与えれば常に同じ値が出ます。

パーリンノイズの周期を調整して2~4つ重ねることでそれっぽい地形を無限で生成することができます。

バイオームを分けるのは難しいです。
簡単にできる方法としてはボロノイノイズを使うのが良いですが、直線的になってしまいます。

しかし、Beta1.8以降はかなり複雑です。海沿いにビーチバイオームなどがあり、生成の基準がバイオームになっています。
これは今度解説することにします。

スナップショットとか

スナップショットとか明日頃出るらしい。
1.13……、コマンドの修正なんか結構あるらしいですねぇ。

一応対応ツールを作っているんですが、まだ全然進捗がない。

ううむ時間かかりそうです。

コマンド仕掛けをつくってアップデートで阿鼻叫喚する。大変そうです。うむ。厳しい。

なんというかまだまだできる望みがかなり薄いので、参考までにどんな感じの実装になるかを。

テキストファイルにもとのデータの形と今のデータの形のプリセットファイルを置いてそこから、前のコマンド引数が後のコマンド引数でどの場所に位置するかを読み込みます。

そこから、SNLなどを利用して、ワールド内の全コマンドファイルを羅列して、プリセットに合致するものがアレば引数の順番を入れ替える。

しかしexecuteコマンドがかなり曲者です。再帰処理が必要そう。あと1.13でよくわからん。
私もexecuteの処理をなんとかすれば行けそうな感じではある。

誰か他に作っている人がいたらぜひ頑張って欲しいなぁ。と
あとは任せた。

ShrinkTool

ShrinkBlockのMCEditが使えないとかまあいろいろある人向けにツールを作りました。
.net無いと動きません!

schematicファイルやストラクチャーブロックのデータをご用意してください!
まあその後は使ってみればわかります。
基本的な使い方はMCEdit版とまったくもって同じ

無保証。

基本的にアレ、最新版までブロックデータしか入っていないので、まあそのうち更新します

ダウンロードはこちら
ShrinkTool

それにしても1.13のコマンドアプデが辛辣です
以上。

ShrinkBlocks

ShrinkBlocksのサルベージ+機能追加。
アーマースタンドでちっちゃいブロックとか作れます。
たくさん並べると重くなるので注意してください。
無保証です。

使い方:MCEditのfilterの入ってるフォルダーに入れる

オプション:
・サイズはサイズ。使ってみるべし。
・Invisible、見えなくする。オフにするとアーマースタンド本体がみえる。
・Lightenで中をくりぬきます。ちょっとは軽くなる。たまにバグる。
・Scraping Terrainでもとのブロックを消します。きをつけてね。

バックアップして使うこと。何が起きてもわからん。
階段などの向き補正はしてない。

ダウンロード:
ShrinkBlocksImproved