LoginSignup
6
4

More than 3 years have passed since last update.

[Java]MinecraftのModを作成しよう 1.16.1【ブロックの追加】

Posted at

(この記事は一連の解説記事の一つになります)

先頭記事:入門編
前の記事:アイテムの追加
次の記事:

ブロックの追加

ブロックの追加をします。1.14.4のときと少し書き方を変えました(バージョンアップによって実装の方法が変わったという意味ではないです)。

ブロックの登録

\src\main\java\jp\koteko\liveinwater\
   ├ block
   │   └ Blocks.java
   ├ item
   └ LiveInWater.java
Blocks.java
package jp.koteko.liveinwater.block;

import jp.koteko.liveinwater.LiveInWater;
import net.minecraft.block.AbstractBlock;
import net.minecraft.block.Block;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraftforge.event.RegistryEvent;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

import java.util.ArrayList;
import java.util.List;

@Mod.EventBusSubscriber(modid = LiveInWater.MOD_ID, bus = Mod.EventBusSubscriber.Bus.MOD)
public class Blocks {
    public static List<Block> blockList = new ArrayList<Block>();
    public static Block WATERTREE_ROOT_BLOCK = register("watertree_root_block", new Block(AbstractBlock.Properties.create(Material.WOOD).hardnessAndResistance(2.5F).sound(SoundType.WOOD)));

    private static Block register(String key, Block blockIn){
        blockList.add(blockIn);
        return blockIn.setRegistryName(LiveInWater.MOD_ID, key);
    }

    @SubscribeEvent
    public static void registerBlocks(RegistryEvent.Register<Block> event) {
        for (Block block : blockList) {
            event.getRegistry().register(block);
        }
    }
}

前回のアイテム登録と同様のことをブロックについて行います。
宣言・初期化と同時にListにアイテムを追加し、forループでリストのアイテムをすべてregister()します。
単なる無機能ブロックの場合Blockクラスのインスタンスとします。コンストラクタの引数にはAbstractBlock.Propertiesのインスタンスを与えます。

アイテムの登録

\src\main\java\jp\koteko\liveinwater\
   ├ block
   ├ item
   │   └ Items.java
   └ LiveInWater.java
Items.java
package jp.koteko.liveinwater.item;

import jp.koteko.liveinwater.LiveInWater;
import jp.koteko.liveinwater.block.Blocks;
import net.minecraft.block.Block;
import net.minecraft.item.BlockItem;
import net.minecraft.item.Item;
import net.minecraft.item.ItemGroup;
import net.minecraftforge.event.RegistryEvent;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

import java.util.ArrayList;
import java.util.List;

@Mod.EventBusSubscriber(modid = LiveInWater.MOD_ID, bus = Mod.EventBusSubscriber.Bus.MOD)
public class Items {
    public static List<Item> itemList = new ArrayList<Item>();
    public static final Item WATERTREE_ROOT = register("watertree_root", new Item((new Item.Properties()).group(ItemGroup.MATERIALS)));
    public static final Item WATERTREE_ROOT_BLOCK = register("watertree_root_block", Blocks.WATERTREE_ROOT_BLOCK, ItemGroup.BUILDING_BLOCKS);

    private static Item register(String key, Item itemIn) {
        itemList.add(itemIn);
        return itemIn.setRegistryName(LiveInWater.MOD_ID, key);
    }
    private static Item register(String key, Block blockIn, ItemGroup itemGroupIn) {
        return register(key, new BlockItem(blockIn, (new Item.Properties()).group(itemGroupIn)));
    }

    @SubscribeEvent
    public static void registerItems(RegistryEvent.Register<Item> event) {
        for (Item item : itemList) {
            event.getRegistry().register(item);
        }
    }
}

ブロックは同時にアイテムとしても存在するので、アイテムも登録します。
registerメソッドをオーバーロード(異なる引数による同名メソッドの定義)してブロックアイテムの登録が行いやすいようにしました。登録名、ブロック、アイテムグループを渡すと、中でグループを設定したBlockItemをつくり、アイテムのregisterに投げるようにします。
BlockItemItemのサブクラスで、アイテムとしてのブロックはこのクラスのインスタンスとします。

resourcesの設定

\src\main\resources
   └ assets
      └ liveinwater
         ├ blockstates
         │  └ watertree_root_block.json
         ├ lang
         │  └ en_us.json
         │  └ ja_jp.json
         ├ models
         │  ├ block
         │  │  └ watertree_root_block.json
         │  └ item
         │     └ watertree_root_block.json
         └ textures
            ├ block
            │  └ watertree_root_block.png
            └ item
lang\en_us.json
{
  "item.liveinwater.watertree_root_block": "WaterTree Root"
}
lang\ja_jp.json
{
  "item.liveinwater.watertree_root_block": "ウォーターツリーの根"
}
blockstates\watertree_root_block.json
{
  "variants": {
    "": { "model": "liveinwater:block/watertree_root_block" }
  }
}

"model": "[MOD_ID]/[モデルファイルのパス]"
ブロックの状態によってモデルを変えるような場合(たとえば、方向を持つブロックや、フェンスなどの連結するブロック)にはこのファイルを編集しますが、不要な場合このような形です。

models\block\watertree_root_block.json
{
  "parent": "block/cube_all",
  "textures": {
    "all": "liveinwater:block/watertree_root_block"
  }
}

[MOD_ID]:[テクスチャファイルのパス]
parentblock/cube_allを指定します。
これは単純な立方体のモデルで、全面に同じテクスチャを反映します。

models\item\watertree_root_block.json
{
  "parent": "liveinwater:block/watertree_root_block"
}

ブロックアイテムはparentにブロックのモデルファイルを指定すればよいです。

watertree_root_block.png
テクスチャを作成し、配置します。

ルートテーブルの設定

Minecraft 1.9以降ではドロップを管理する仕組みとしてルートテーブルが導入されました。ブロックのドロップもこれを使って設定します。

\src\main\resources
   ├ assets
   └ data
      └ liveinwater
         └ loot_tables
            └ blocks
               └ watertree_root_block.json

前の記事で用意しておいたdata\liveinwaterフォルダ内にblocks\watertree_root_block.jsonを配置します。

watertree_root_block.json
{
  "type": "minecraft:block",
  "pools": [
    {
      "rolls": 1,
      "conditions": [
        {
          "condition": "minecraft:match_tool",
          "predicate": {
            "enchantments": [
              {
                "enchantment": "minecraft:silk_touch",
                "levels": {
                  "min": 1
                }
              }
            ]
          }
        }
      ],
      "entries": [
        {
          "type": "minecraft:item",
          "name": "liveinwater:watertree_root_block"
        }
      ]
    },
    {
      "rolls": 1,
      "conditions": [
        {
          "condition": "minecraft:inverted",
          "term": {
            "condition": "minecraft:match_tool",
            "predicate": {
              "enchantments": [
                {
                  "enchantment": "minecraft:silk_touch",
                  "levels": {
                    "min": 1
                  }
                }
              ]
            }
          }
        }
      ],
      "entries": [
        {
          "type": "minecraft:item",
          "functions": [
            {
              "function": "minecraft:apply_bonus",
              "enchantment": "minecraft:fortune",
              "formula": "minecraft:binomial_with_bonus_count",
              "parameters": {
                "extra": 3,
                "probability": 0.5714286
              }
            }
          ],
          "name": "liveinwater:watertree_root"
        }
      ]
    },
    {
      "rolls": 1,
      "conditions": [
        {
          "condition": "minecraft:inverted",
          "term": {
            "condition": "minecraft:match_tool",
            "predicate": {
              "enchantments": [
                {
                  "enchantment": "minecraft:silk_touch",
                  "levels": {
                    "min": 1
                  }
                }
              ]
            }
          }
        }
      ],
      "entries": [
        {
          "type": "minecraft:item",
          "name": "minecraft:dirt"
        }
      ]
    }
  ]
}

「シルクタッチのツールで破壊した場合ブロックそのもの(watertree_root_block)を、それ以外の場合は土ブロック(dirt)1つとアイテム(watertree_root)をランダム個ドロップする」という例です。詳しい説明は参考ページに譲ります。
(色々と試しましたが重複する記述があり冗長な書き方である可能性があります。)

最小の構成はこのようになります。
ブロック自身をドロップする最小構成のルートテーブル
{
  "type": "minecraft:block",
  "pools": [
    {
      "rolls": 1,
      "entries": [
        {
          "type": "minecraft:item",
          "name": "[MOD_ID]:[ITEM_NAME]"
        }
      ]
    }
  ]
}

typeは何に関するルートテーブルかを選択する。poolsに与えた各プールが順次適応され、rolls回の抽選によってentriesに与えた各エントリーから結果が選ばれる。エントリーでtypenameを返すと指定。

確認

ゲームを起動して確認します。
キャプチャ.PNG
ブロックとそのアイテムの追加ができていること、表示が正しいこと、シルクタッチでブロックそのもの・非シルクタッチで土とアイテムがドロップすることが確認できました。

参考

[Java]MinecraftのModを作成しよう 1.14.4【2. ブロックの追加】
Minecraft 1.14.4 Forge Modの作成 その4 【ブロックの追加】
ルートテーブル - Minecraft Wiki
loot_tables_1.14.md · GitHub

次の記事

6
4
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
4