Создание модификаций с помощью ModLoader (Beta 1.7.3)
Подготовка
Вам нужно скачать следующее:
Инструмент | Скачать |
JDK | Скачать |
RetroMCP-Java | Скачать (Github) |
ModLoader (MCBeta 1.7.3) | Скачать (GitHub) |
ModLoaderMP Client (MCBeta 1.7.3) | Скачать (Mediafire) |
ModLoaderMP Server (MCBeta 1.7.3) | Скачать (Mediafire) |
Sublime Text или Notepad++ | Скачать (SublimeText) / Скачать (NP++) |
Подготовка RetroMCP
RetroMCP — переписанный, кроссплатформенный Mod Coder Pack (MCP).
Убедитесь что в ваш провайдер не заблокировал добрую часть интернета. Если RetroMCP что-то не сможет скачать то декомпиляция вылетит с ошибкой.
- Переместите скачанный jar файл RetroMCP в новую папку и откройте его. Желательно чтобы путь к папке с MCP не содержал символов Кириллицы
- Если вы всё сделали правильно, перед вами откроется Командная строка или Power Shell. Иначе jar либо не откроется, либо выдаст ошибку.
- Введите setup, дождитесь пока MCP создаст все нужные папки и затем впишите b1.7.3.
- В создавшемся рабочем пространстве найдите папку jars и перейдите в неё. Откройте архиватором (7-Zip или WinRar) файл minecraft.jar, удалите из него папку META-INF и распакуйте в него ModLoader.
- После распаковки ModLoader, распакуйте ModLoaderMP Client в jar и закройте архиватор.
- Затем повторите такие-же действия с minecraft_server.jar, только не нужно распаковывать сам ModLoader, а вместо ModLoaderMP Client нужно распаковать Server.
- Откройте RetroMCP, если вы его закрыли ранее и введите decompile. Через пару секунд (или минут :^)) исходный код Minecraft и его сервера появится в папке (Папка MCP)/src.
Создание мода
Главный класс
Главный класс клиентского мода должен находиться в папке (MCP)/src/minecraft/net/minecraft/src/.
Создаём класс, обязательно называем его mod_###.java. ### нужно заменить на имя вашего мода без пробелов. Я буду использовать идентификатор testmod.
Код главного класса:
package net.minecraft.src;
public class mod_### extends BaseMod
{
public mod_###()
{
ModLoader.SetInGameHook(this, true, false);
}
public String Version()
{
return "1.0"; // Версия мода, не рекомендую добавлять кириллические символы и "-".
}
}
package net.minecraft.src;
— «папка» в которой находятся все классы или исходный код. В нашем случае нельзя изменять.
extends BaseMod
— наследуем класс BaseMod. Это нужно чтобы мод работал и определялся правильно.
public mod_###()
— конструкор класса нашего мода, в нём в будущем мы будем регистрировать Блоки, Предметы, Броню и так далее.
ModLoader.SetInGameHook(this, true, false);
— «инициализатор» мода. С помощью него ModLoader знает что указанный класс — это мод и загружает его.
this — BaseMod, путь к классу мода. У нас это this, так как мы работаем с нашим модом который наследует класс BaseMod.
true — включает или отключает (если значение false) мод.
false — этап на котором загружается мод. Если значение — true, запуск будет только один раз за каждый тик, если false — один раз в каждом кадре.
Создание блока
Есть два метода регистрации блоков:
- Первый — без создания специального класса для блока.
- Второй — с созданием класса блока.
Первый больше подходит при создании блока-затычки, или обычного строительного блока с одной текстурой. А второй, когда нужно создать блок с каким-либо назначением. Например, открытие интерфейса или создание сигнала красного камня.
Первый способ
Добавляем после определения класса:
public static Block testblock;
Здесь мы создаём основу для блока, testblock — это идентификатор нашего блока. Он будет использоваться для регистрации, установки имени и текстуры.
Дальше, в конструктор нашего главного класса добавляем:
testblock = new Block(100, 0, Material.rock).setStepSound(Block.soundStoneFootstep).setBlockName("testblock").setHardness(1.0F).setResistance(10F);
testblock.blockIndexInTexture = ModLoader.addOverride("/terrain.png", "/assets/myblock.png");
ModLoader.RegisterBlock(testblock);
ModLoader.AddName(testblock, "TESTEFICATE");
Добавляем блок
new Block(100, 0, Material.rock)…
100 — ID блока который мы добавляем. До выхода снапшота 13w02a все текстуры хранились в файлах «/terrain.png» и «/gui/items.png». Максимальное количество текстур в них — 256 (16*16).
Зачем-то список ID блоков был ограничен до 256, хотя слотов для предметов доступно 32000. Если ID вашего блока пересечётся с ID блока другого мода — то… В общем, ничего хорошего.
0 — Индекс текстуры в файле «/terrain.png», мы не будем это использовать, так что оставляем 0. 0 — камень.
Material.rock — Материал для блока. Каждый из доступных материалов имеет свои особенности и свойства. Вот список всех доступных материалов:
Материал | Блок | Особенности |
air | Воздух | Нет особенностей |
grassMaterial | Трава | Нет особенностей |
ground | Земля | Нет особенностей |
wood | Дерево | Воспламеняется |
stone | Камень | Ничего не вырастет (в коде стоит флаг .setNoHarvest()) |
iron | Железо | Ничего не вырастет |
water | Вода | Не полный блок |
lava | Лава | Не полный блок |
leaves | Листва | Воспламеняется, Полупрозначный, Не полный блок (Запрет спавна сущностей) |
plants | Растения | Не полный блок |
sponge | Губка | Имеет такой-же цвет как у шерсти. |
cloth | Шерсть | Воспламеняется |
fire | Огонь | Не полный блок, не отображается на карте |
sand | Песок | Нет особенностей |
circuits | Факела, кнопки, рельсы, лестницы | Не отображается на карте, Имеет техническое назначение |
glass | Стекло | Полупрозрачный |
tnt | Динамит | Воспламеняется, Полупрозначный (?) |
field_4262_q | ? | Не используется |
ice | Лёд | Полупрозрачный |
snow | Снежный ковёр | Не полный блок, Ничего не вырастет, Полупрозрачный, «Ковровый» |
builtSnow | Блок снега | Ничего не выростет |
cactus | Кактус | Полупрозрачный, Не полный блок |
pumpkin | Тыква | Не полный блок (?) |
portal | Портал в незер | Не отображается на карте, Не замедляет движение при прохождении |
cakeMaterial | Торт | Не отображается на карте, Не полный блок |
field_31068_A | Паутина | Ничего не вырастет, Не полный блок |
field_31067_B | Поршень | Имеет техническое назначение |
- .setStepSound(Block.?); — звук который воспроизводится при хождении по блоку ? нужно заменить на 1 из существующих.
В Бете 1.7.3 существует 9 видов звука хождения:
Звук | Блок(-и) |
soundPowderFootstep | Звук хождения по красному камню. |
soundWoodFootstep | Звук хождения по дереву. |
soundGravelFootstep | Звук хождения по гравию. |
soundGrassFootstep | Звук хождения по траве. |
soundStoneFootstep | Звук хождения по камню и остальным блокам для которых не установлен уникальный звук. |
soundMetalFootstep | Звук хождения по золоту, алмазам, рельсам, железной двери и спаунеру. |
soundGlassFootstep | Звук хождения по льду, светокамню и порталу в незер. |
soundClothFootstep | Звук хождения по шерсти, снегу, кактусу и торту. |
soundSandFootstep | Звук хождения по песку и песку душ. |
- .setBlockName(«testblock») — Имя блока, использвуется для получения имени из файла локализации. В нашем случае мы будем устанавливать имя блока после регистрации, так что можно не именять.
- .setHardness(1.0F) — Упругость блока при ломании. 1.0F — уровень упругости, например у камня — «1.5F». F нужно добавлять обязательно, иначе будут ошибки при компиляции.
- .setResistance(10F) — Взрывоустойчивость блока, чем выше, тем меньше шанс уничтожения блока взрывом. У обсидиана, к примеру — 6000F, динамит уничтожить его не может.
Дополнительные флаги
- .setLightOpacity(?) — Уровень поглащения света блоком (требуется уточнить)
- .setLightValue(?F) — Уровень света издаваемый блоком. Установленное значение «?» умножается на 15.
- .setBlockBounds(x, y, z, x1, y1, z1) — Границы блока, об этом поговорим позже.
Текстура блока
- testblock.blockIndexInTexture = ModLoader.addOverride(«/terrain.png», «/assets/myblock.png»); — Здесь мы говорим ModLoader`у что требуется перезаписать текстуру «/terrain.png» файлом «/assets/myblock.png». blockIndexInTexture — индекс текстуры в файле «/terrain.png», у нас это 0. «/assets/myblock.png» — это текстура 16x16, как в новой версии. Папка «/assets/» должна находиться внутри minecraft.jar, но вы можете изменить «/assets/» на любую папку которую захотите.
Регистрируем блок
- ModLoader.RegisterBlock(testblock); — Регистрируем блок, testblock — идентификатор блока который мы указали раннее.
- ModLoader.AddName(testblock, «TESTEFICATE»); — Тут как обычно, testblock — идентификатор блока, а «TESTEFICATE» это имя блока отображаемое в игре.
Второй способ
Второй способ добалвениы блока не сильно отличается от первого, за исключением того что придётся заменить new Block(… на new Block$$$(…, где $$$ — любое нужное вам имя.
Заходим в (MCP)/src/minecraft/net/minecraft/src/ и создаём в нём Block$$$.java
Я буду использовать вместо $$$ — MyBLK. Создаю класс BlockMyBLK.java
Открываем и пишем:
package net.minecraft.src;
import java.util.Random;
public class BlockMyBLK extends Block
{
protected BlockMyBLK(int id, int texind, Material mat)
{
super(id, texind, mat);
blockIndexInTexture = ModLoader.addOverride("/terrain.png", "/assets/test.png");
}
public int idDropped(int i, Random random)
{
return mod_testmod.myblk.blockID;
}
public int quantityDropped(Random random)
{
return 1;
}
}
Теперь разбираемся.
import java.util.Random;
— мы импортируем это так как некотерые функции требуют Random, он пригодится позже когда будем создавать звук для блока.
extends Block
— мы наследуем класс Block, это нужно для правильной работы и так далее.
super(id, texind, mat);
— мы обращаемся в класс Block и отправляем ему ID блока, индекс текстуры и материал блока.
blockIndexInTexture = ModLoader.addOverride("/terrain.png", "/assets/test.png");
— нам проще будет задавать текстуру для блока внутри класса, так как это в будущем пригодится для создания блока с разными текстурами.
public int idDropped(int i, Random random)
— что будет выпадать из блока. Если в return вставить 0, то ничего не выпадет. В нашем случае из блока падает этот же самый блок.
Если вам нужно чтобы из блока падал предмет, например алмаз, тогда замените mod_testmod.testblock.blockID на Item.diamond.shiftedIndex.
public int quantityDropped(Random random)
— количество выпадаемого из блока.
Регистрируем блок
В начале класса как и раньше добавляем:
public static Block myblk;
В конструктор класса добавляем:
myblk = new BlockMyBLK(101, 0, Material.glass).setStepSound(Block.soundStoneFootstep).setBlockName("myblock").setHardness(0.5F).setResistance(2F);
ModLoader.RegisterBlock(myblk);
ModLoader.AddName(myblk, "CLASSBLOCK");
Заменяем Block(100… на BlockMyBLK(101….
100 на 101 мы заменили потому что для каждого блока нужен свой ID. Если вы не будете его изменять то у вас будут ошибки и вылеты. Также, я заменил материал с камня на стекло, для примера.
Создание своего материала для блока
Создавать свой материал может быть полезно когда вы делаете новые блоки, у которых будут специальные фишки, или когда вы делаете жидкости.
Всего существует пять видов материала:
Название | Назначение |
Material | Материал для блока |
MaterialLiquid | Материал для жидкости |
MaterialLogic | Материал для блоков с особанными свойствами |
MaterialPortal | Материал для портала |
MaterialTransparent | Материал для блока с прозрачной текстурой |
И так, как же выглядит код для материала:
public static final Material [имя материала] = new [класс материала](MapColor.[цвет на карте])
[имя материала] — любое имя для нового маатериала, главное как обычно без кириллических символов и пробелов.
[класс материала] — нужный вам класс для материала, берите из исходников или из таблицы выше.
[цвет на карте] — цвет которым будет обозначен блок на карте. Всего существует 14 вариантов цвета:
Код | Цвет | Особенности |
airColor | Нет | Не отображается на карте |
grassColor | #7FB238 | Нет |
sandColor | #F7E9A3 | Нет |
clothColor | #A7A7A7 | Нет |
tntColor | #FF0000 | Нет |
iceColor | #A0A0FF | Нет |
ironColor | #A7A7A7 | Нет |
foliageColor | #007C00 | Нет |
snowColor | #FFFFFF | Нет |
clayColor | #A4A8B8 | Нет |
dirtColor | #B76A2F | Нет |
stoneColor | #707070 | Нет |
waterColor | #4040FF | Нет |
woodColor | #685332 | Нет |
Ещё, для материалов требуются свои флаги. Всего есть 5 флагов для материала. Они нужны для более тонкой настройки материала и установки свойств блоку из этого самого материала.
Флаг | Функции |
setIsTranslucent() | Делает текстуру блока прозрачной |
setNoHarvest() | Запрещает сбор блока некорректным инструментом |
setBurning() | Включает воспламеняемость у материала |
setIsGroundCover() | ?. Используется только в материале снежного ковра. |
setNoPushMobility() | Включает не полную проходимость через блок |
setImmovableMobility() | Включает полную проходимость через блок |
Для создания обычного материала можно не добавячть каких-либо флагов, а вот для создания материала жидкости код будет выглядеть так:
public static final Material [имя материала] = new MaterialLiquid(MapColor.[цвет на карте]).setNoPushMobility();
Для блока с прозрачной текстурой код выглядит так:
public static final Material [имя материала] = new Material(MapColor.[цвет на карте]).setIsTranslucent();
А для полностью прозрачного блока так:
public static final Material [имя материала] = new MaterialTransparent(MapColor.[цвет на карте]);
Создание своих звуков для блока
Допустим у нас есть блок для которого обычные звуки не подойдут, мы для решения этой проблемы в тело главного класса добавляем:
public static final StepSound [имя вашего звука] = new StepSound("[идетификатор]", [громкость]F, [тон звука]F);
[имя вашего звука] — текст в ковычках сам про себя говорит, это самое имя мы будем ичпользовать в аргументе .setStepSound() для блоков. «[идентификатор]» — имя вашего звука в папке (Папка Minecraft)/resources/sound/step/. [громкость]F — громкость ваших звуков. (Пример: 1.0F) [тон звука]F — высота звука, заполняется также как и громкость.
Нужные звуки нужно назвать также как и идентификатор, но в конце почле названия добавить число, от 1. Например, идентификатор звука copper, тогда в папке (Папка Minecraft)/resources/step/ будут лежать звуки copper1.ogg, copper2.ogg и т. д.
Создание предмета
Тут как и с блоком существует два способа. С классом и без.
Первый способ
В тело главного класса добавляем:
public static Item myitem;
Регистрируем предмет
В конструктор:
myitem = new Item(1000).setItemName("myitem").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/myitem.png"));
ModLoader.AddName(myitem, "My Super Item");
new Item(1000)… — Создаём предмет, 1000 это ID предмета, в Minecraft Beta 1.7.3 доступно всего 32000 ID для предметов. Я выберу 1000.
.setItemName(«myitem»)… — Имя предмета, опять же используется для получения строчки из файла локализации, у нас будет перезаписано.
.setIconIndex(…); — Устанавливаем иконку для предмета. В … у нас будет: ModLoader.addOverride(«/gui/items.png», «/assets/myitem.png») — Здесь мы перезаписываем «/gui/items.png» файлом с текстурой предмета, а именно: «/assets/myitem.png».
ModLoader.AddName(myitem, «My Super Item») — myitem — идентификатор нашего предмета, а «My Super Item» — имя отображаемое в игре. В общем, всё также как и при создании блока.
Второй способ
Создаём в (MCP)/src/minecraft/net/minecraft/src/ класс нашего предмета. Item$$$.java, где $$$ — любое имя, я буду использовать SuperItem.
Открываем наш файл и пишем:
package net.minecraft.src;
public class ItemSuperItem extends Item
{
protected ItemSuperItem(int id)
{
super(id);
setMaxStackSize(8);
}
}
Разбираемся…
extends Item
— наследуем класс Item.
super(id);
— с помощью этого будем обращаться к классу Item, отсылая ему ID предмета.
setMaxStackSize(8);
— максимальное количество предметов в 1 слоту. Я поставил 8, для примера.
Также существуют и такие флаги:
- setMaxDamage(I); — устанавливаем прочность для предмета. I — прочность.
- setHasSubtypes(BOOL); — имеет ли предмет подтипы (когда берётся его ID и добавляется 1, 2 и так далее). Требует добавления другого конструктора. BOOL — true или false.
- setFull3D(); — устанавливает тип отрисовки предмета. К «полностью 3D» предметам относятся: Инструменты (и Мотыга), Мечи и Удочка.
Регистрируем предмет
В тело главного класса вписываем, как обычно:
public static Item superitem;
В конструктор вписываем тоже самое что и в первом способе, только заменим идентификатор на superitem, Item на ItemSuperItem и ID с 1000 увеличим до 1001.
superitem = new ItemSuperItem(1001).setItemName("superitem").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/superitem.png"));
ModLoader.AddName(superitem, "My Super Item Ever");
Создание еды
Всё также как в первом способе добавления предмета, за исключением пары мелочей.
В тело главного класса:
public static Item sweetBerries;
Регистрируем еду
В конструктор главного класса:
sweetBerries = new ItemFood(1020, 2, false).setItemName("sweetBerries").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/food_sweetBerries.png"));
ModLoader.AddName(sweetBerries, "Sweet Berries");
Самое интересное, в чём же тут различия.
new ItemFood(1020, 2, false)…
1020 уже как должно быть ясно — ID предмета.
2 — количество жизей которое восстанавливает еда.
false — аргумент, отвечающий за пригодность этой еды для Собак. В нашем случае тут: false — это означает что собакам этот вид еды не нравится. Если значение будет true, тогда собаки будут есть эту еду за милую душу.
ПРИМЕЧАНИЕ
Если вы захотите сделать еду складываемой, то добавьте .setMaxStackSize(I) после .setIconIndex, где I — там число. Но будьте осторожны! Складываемая еда в старых версиях не имеет задержки при упортеблении. Это даёт преимущество игроку с которым вы будете драться, а также, например, позволяет выплыть из лавы, если вы будете постоянно употреблять эту еду.
Создание пластинки
Различий также никаких нет, вместо Item пишем ItemRecord, меняем ID и так далее.
В тело главного класса пишем это:
public static Item record@@@;
@@@ меняем на имя вашей пластинки.
Регистрируем пластинку
В конструктор главного класса:
record@@@ = new ItemRecord(2100, "%%%").setItemName("record").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/record_%%%.png"));
new ItemRecord(2100, «%%%»)…
2100 — ID,
«%%%» — имя трека на пластинке. OGG файл с музыкой должен находится в (Папка Minecraft)/resources/streaming/%%%.ogg.
.setItemName(«record»)… — Мы устанавливаем пластинке имя record, в файле локализации record (item.record.name) установлен как Music Disc. Вы также можете добавить своё имя для пластинки. Для этого после установки значения для record@@@ впишите:
ModLoader.AddName(record@@@, "Music Disc - Songs");
Вместо Songs подставьте своё значение.
ПРИМЕЧАНИЕ
Все пластинки будут подписаны от имени C418.
Создание брони
В создании брони также как и почти везде можно использовать два сбособа создания, я буду разбирать тут только один.
В тело главного класса добавляем:
public static Item steelHelmet;
public static Item steelChestplate;
public static Item steelLeggings;
public static Item steelBoots;
Я создаю полный комплект брони, если вам нужен например только шлем, то добавляйте только код шлема.
Регистрация брони
В папку «/armor/» внутри minecraft.jar кладём 2 текстуры, [Тип брони]_1.png и [Тип брони]_2.png. В файле _1 находятся текстуры Нагрудника и Шлема, а в файле _2 текстуры Понож и Ботинок.
В конструктор главного класса вписываем:
steelHelmet = new ItemArmor(3000, 0, ModLoader.AddArmor("steel"), 0).setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/steel_helmet.png")).setItemName("steelHelmet");
steelChestplate = new ItemArmor(3001, 0, ModLoader.AddArmor("steel"), 1).setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/steel_chestplate.png")).setItemName("steelChestplate");
steelLeggings = new ItemArmor(3002, 0, ModLoader.AddArmor("steel"), 2).setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/steel_leggings.png")).setItemName("steelLeggings");
steelBoots = new ItemArmor(3003, 0, ModLoader.AddArmor("steel"), 3).setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/steel_boots.png")).setItemName("steelBoots");
ModLoader.AddName(steelHelmet, "Steel Helmet");
ModLoader.AddName(steelChestplate, "Steel Chestplate");
ModLoader.AddName(steelLeggings, "Steel Leggings");
ModLoader.AddName(steelBoots, "Steel Boots");
new ItemArmor(300#, 0, 0, %)
300(0-3) — ID
0 — Уровень брони, чем выше тем прочнее броня.
ModLoader.AddArmor(«steel») — Это идентификатор нашей брони. Он используется потому что нам нужно регистрировать новые текстуры для брони. ModLoader присваивает числовое значение к тому что вы ввели в скобках. В Minecraft уже есть массив с текстурами брони, если мы будем использовать его то нам придётся заменять оригинальные текстуры, а это не интересно.
% — Тип предмета.
0 — Шлем.
1 — Нагрудник.
2 — Поножи.
3 — Ботинки.
Прочность брони вычисляется по формуле [Тип брони] * 3 << [Уровень брони]. << — оператор битового сдвига влево.
Предмет | Прочность (По типу брони) |
Шлем | 11 |
Нагрудник | 16 |
Поножи | 15 |
Ботинки | 13 |
Вот таблица значений в Minecraft Beta 1.7.3:
Тип | ID (В коде) | ID (В игре) | Уровень брони | Идентификатор | Тип предмета |
Кожаный шлем | 42 | 298 | 0 | 0 | 0 |
Кожаный нагрудник | 43 | 299 | 0 | 0 | 1 |
Кожаные поножи | 44 | 300 | 0 | 0 | 2 |
Кожаные ботинки | 45 | 301 | 0 | 0 | 3 |
Кольчужный шлем | 46 | 302 | 1 | 1 | 0 |
Кольчужный нагрудник | 47 | 303 | 1 | 1 | 1 |
Кольчужные поножи | 48 | 304 | 1 | 1 | 2 |
Кольчужные ботинки | 49 | 305 | 1 | 1 | 3 |
Железный шлем | 50 | 306 | 2 | 2 | 0 |
Железный нагрудник | 51 | 307 | 2 | 2 | 1 |
Железные поножи | 52 | 308 | 2 | 2 | 2 |
Железные ботинки | 53 | 309 | 2 | 2 | 3 |
Алмазный шлем | 54 | 310 | 3 | 3 | 0 |
Алмазный нагрудник | 55 | 311 | 3 | 3 | 1 |
Алмазные поножи | 56 | 312 | 3 | 3 | 2 |
Алмазные ботинки | 57 | 313 | 3 | 3 | 3 |
Золотой шлем | 58 | 314 | 1 | 4 | 0 |
Золотой нагрудник | 59 | 315 | 1 | 4 | 1 |
Золотые поножи | 60 | 316 | 1 | 4 | 2 |
Золотые ботинки | 61 | 317 | 1 | 4 | 3 |
ПРИМЕЧАНИЕ
В Minecraft железная броня называется «[Элемент брони]steel».
Создание инструментов и оружия
Для всех инструментов существует таблица материалов:
Материал | Уровень добычи | Прочность (Все предметы) | Эффективность на правильном материале | Урон по сущности |
WOOD | 0 | 59 | 2.0F | 0 |
STONE | 1 | 131 | 4.0F | 1 |
IRON | 2 | 250 | 5.0F | 2 |
EMERALD | 3 | 1561 | 8.0F | 3 |
GOLD | 0 | 32 | 12.0F | 0 |
EMERALD — Материал алмазных инструментов
Создание меча
В тело гл. класса как обычно добавляем:
public static Item obsidianSword;
Я буду добавлять обсидиановые инструменты. Замените obsidian на любое другое название, если хотите конечно.
obsidianSword = new ItemSword(3800, EnumToolMaterial.EMERALD).setItemName("obsidianSword").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/obsidian_sword.png"));
ModLoader.AddName(obsidianSword, "Obsidian Sword");
new ItemSword(3800, EnumToolMaterial.EMERALD)…
- 3800 — ID.
- EnumToolMaterial.EMERALD — Материал меча, в моём случае это EMERALD, так как материала лучше пока что нет.
Создание инструментов (Кирка, Топор, Лопата, Мотыги)
Тело:
public static Item obsidianPickaxe;
public static Item obsidianAxe;
public static Item obsidianSpade;
public static Item obsidianHoe;
Конструктор:
obsidianPickaxe = new ItemPickaxe(3801, EnumToolMaterial.EMERALD).setItemName("obsidianPickaxe").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/obsidian_pickaxe.png")); // Кирка
obsidianPickaxe = new ItemPickaxe(3802, EnumToolMaterial.EMERALD).setItemName("obsidianPickaxe").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/obsidian_axe.png")); // Топор
obsidianPickaxe = new ItemPickaxe(3803, EnumToolMaterial.EMERALD).setItemName("obsidianPickaxe").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/obsidian_spade.png")); // Лопата
obsidianPickaxe = new ItemPickaxe(3804, EnumToolMaterial.EMERALD).setItemName("obsidianPickaxe").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/obsidian_hoe.png")); // Мотыга
ModLoader.AddName(obsidianPickaxe, "Obsidian Pickaxe");
ModLoader.AddName(obsidianAxe, "Obsidian Axe");
ModLoader.AddName(obsidianSpade, "Obsidian Shovel");
ModLoader.AddName(obsidianHoe, "Obsidian Hoe");
Создание ножниц и ведра
При создании ножниц или удочки нельзя указать ничего интересного, поэтому сделаем сурер-ножницы из дерева с 3000 прочности.
Ножницы
Тело гл. класса:
public static Item woodenShears;
Конструктор гл. класса:
woodenShears = (ItemShears)(new ItemShears()).setItemName("woodenShears").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/woodenshears.png")).setMaxDamage(2999);
ModLoader.AddName(woodenShears, "Wooden Shears");
Значение .setMaxDamage установлено на 2999 потому что в старых версиях предмет с прочностью 0 считался исправным, так что по логике 0+2999=3000.
Ведро
Тело:
public static Item bucketDirt;
Конструктор:
bucketDirt = new ItemBucket(3555, Block.dirt.blockID).setItemName("bucketDirt").setIconIndex(ModLoader.addOverride("/gui/items.png", "/assets/bucketdirt.png")).setContainerItem(Item.bucketEmpty);
ModLoader.AddName(bucketDirt, "Dirt Bucket");
new ItemBucket(3555, Block.dirt.blockID)…
3555 — ID.
Block.dirt.blockID — ID блока который содержется в этом ведре. Можно зменить на любой блок из игры, или соданный в моде.
- .setContainerItem(Item.bucketEmpty) — Предмет на который будет заменено ведро при «выливании». Если вы создали до этого пустое ведро, то замените Item.bucketEmpty на mod_[имя вашего мода].[идентификатор предмета-ведра].
Создание рецептов
Существует возможность создать всего 3 вида рецептов, а именно: Обычный крафт, Бесформенный крафт и Выплавка.
Создание обычного крафта
Для примера я буду в качестве рецепта использовать палку и железный блок, а в качестве результата — камень.
Теперь, как это будет выглядеть в коде:
ModLoader.AddRecipe(new ItemStack(Block.stone, 1), new Object[] { "I ", " S ", " I", 'I', Block.blockSteel, 'S', Item.stick });
new ItemStack(Block.stone, 1) — результат получившегося.
Block.stone — результат крафта.
1 — количество получившегося.
new Object[] {…} — массив создания. Массив создания представляет собой сетку крафта, разложеную на символы в скобках.
"I "
" S "
" I"
Ингредиенты | Рецепты крафта |
---|---|
Железный блок + Палка |
Также рецепт можно создать в сетке 2x2. Для этого достаточно сократить количество символов и убрать 1 пару скковычек.
"I "
" S"
Ингредиенты | Рецепты крафта |
---|---|
Палка + Железный блок |
'I', Block.blockSteel — обозначение первого символа крафта. В моём случае I — это железный блок.
'S', Item.stick — также как и в первом случае это обозначение символа. Тут у нас S — палка.
Никто также не запрещает использовать свои предметы и блоки, требуется вместо условного Block.blockSteel или Item.stick подставить идентификатор своего предмета/блока.
Создание бесформенного крафта
Всё почти идентично добавлению обычного крафта, за исключением нескольких отличий. Тут для примера я буду использовать алмаз, обсидиан и камень для получения 4х коренной породы.
ModLoader.AddShapelessRecipe(new ItemStack(Block.bedrock, 4), new Object[] { Item.diamond, 1, Block.obsidian, 1, Block.stone, 1 });
Ингредиенты | Рецепты крафта |
---|---|
Алмаз + Камень + Обсидиан |
Item.diamond, 1,
Block.obsidian, 1,
Block.stone, 1
Здесь мы через ,
указываем ингредиенты и их количество.
Использование красителей в рецепте
Для использование красителей в рецепте нам нужно в массив рецепта вместо ID нашего предмета вставить специальный конструктор:
new ItemStack(Item.dyePowder, 1, %)
Где % там число от 0 до 15. Это число — метадата предмета. Все цвета можно найти в этой таблице:
ID | Цвет |
0 | Чёрный |
1 | Красный |
2 | Зелёный |
3 | Коричневый |
4 | Синий |
5 | Фиолетовый |
6 | Циановый |
7 | Светло-серый |
8 | Серый |
9 | Розовый |
10 | Лаймовый |
11 | Жёлтый |
12 | Голубой |
13 | Пурпурный |
14 | Оранжевый |
15 | Белый |
Если вы хотите использовать шерсть вместо красителя тогда таблица цвета будет перевёрнутой, тоесть 0-белый, 1-оранжевый и т. д.
Создание рецепта выплавки
Рецепт выплвки значительнр отличается от других рецептов своей структурой, здесь я буду использовать землю как ингредиент, а результатом будут трое золотых блоков.
ModLoader.addSmelting(Block.dirt.blockID, new ItemStack(Block.blockGold, 3));
Ингредиенты | Процесс |
---|---|
Земля |
Ну а вот и главные отличия, нам не нужно создавать Object массив для создания самого рецепта.
Block.dirt.blockID — ID блока который будет использован для получения результата. Если в вашем рецепте используется предмет, а не блок, то нужно заменить .blockID на .shiftedIndex.
new ItemStack(Block.blockGold, 3) — конструктор продукта рецепта. Block.blockGold — идентификатор блока который будет получен в результате, а 3 — количество этого самого результата.