• Minecraft Forge编程入门三 “初始化项目结构和逻辑”


    经过前面两个教程Minecraft Forge编程入门一 “环境搭建”Minecraft Forge编程入门二 “工艺和食谱”,我们大体知道了如何自定义合成配方,主要是在
    Mod类的init方法中进行注册,但可想而之随着项目的进行需要注册的内容会越来越多,全部写在init中会显得Mod类很臃肿。作为一个优秀的程序员可定不能容忍这种事情发生,那么接下来我们对我们的工程进行一下重构。

    看一下重构后的代码结构:

    源码包的处理

    在我的工程中,我的包名时com.zql.mc.zmod,这个大家可以自己定义。
    我们先看一下ZMod.java这个类:

    package com.zql.mc.zmod;
    
    import net.minecraftforge.fml.common.Mod;
    import net.minecraftforge.fml.common.SidedProxy;
    import net.minecraftforge.fml.common.Mod.EventHandler;
    import net.minecraftforge.fml.common.event.FMLInitializationEvent;
    import net.minecraftforge.fml.common.event.FMLPostInitializationEvent;
    import net.minecraftforge.fml.common.event.FMLPreInitializationEvent;
    
    /**
    *
    *告诉FML我们的Mod的相关信息,这里我的modid为ZMod,版本号是1.0,名字是ZMod
    */
    @Mod(modid = ZMod.MOD_ID, version = ZMod.VERSION, name = ZMod.MOD_NAME)
    public class ZMod {
        public static final String MOD_ID = "ZMod";
        public static final String VERSION = "1.0";
        public static final String MOD_NAME = "ZMod";
    
        //让FML为我们初始化
        @Mod.Instance(value = ZMod.MOD_ID)
        public static ZMod instance;
    
        //告诉FML,对于本地和服务端,proxy分别用ClientOnlyProxy和DedicatedServerProxy进行初始化。
        @SidedProxy(clientSide = "com.zql.mc.zmod.ClientOnlyProxy", serverSide = "com.zql.mc.zmod.DedicatedServerProxy")
        public static CommonProxy proxy;
    
        //在我们的mod被加载的时候会按preInit,init和postInit的顺序执行这三个方法。
        //preInit主要用于读取本地配置,创建方块,物品等并注册他们。
        @EventHandler
        public void preInit(FMLPreInitializationEvent event) {
            proxy.preInit();
        }
    
        //init主要用于构建一些我们自定义的数据类型,注册自定义合成方法,和其它一些操作。
        @EventHandler
        public void init(FMLInitializationEvent event) {
            proxy.init();
        }
    
        //与其它mod进行交互,完成我们mod最后的处理
        @EventHandler
        public void postInit(FMLPostInitializationEvent event) {
            proxy.postInit();
        }
    }
    
    

    对代码的解释我都写在相应位置,请仔细阅读。
    接着介绍三个类:CommonProxy,ClientOnlyProxyDedicatedServerProxy

    • CommonProxy:用于初始化mod,并使它能够正常运行。CommonProxy的代码同时在本地和服务端运行。
      其中preInit,init和postInit分别对应Mod中的三个方法。
    package com.zql.mc.zmod;
    
    import net.minecraft.entity.player.EntityPlayer;
    
    public abstract class CommonProxy {
    
        public void preInit() {
        }
    
        public void init() {
        }
    
        public void postInit() {
        }
    
        abstract public boolean playerIsInCreativeMode(EntityPlayer player);
    
    }
    
    • ClientOnlyProxy:继承CommonProxy,在它的基础上做一些只有client端需要处理的事情如方块的渲染工作等。
    package com.zql.mc.zmod;
    
    import net.minecraft.client.Minecraft;
    import net.minecraft.client.entity.EntityPlayerSP;
    import net.minecraft.entity.player.EntityPlayer;
    import net.minecraft.entity.player.EntityPlayerMP;
    
    public class ClientOnlyProxy extends CommonProxy {
    
        public void preInit() {
            super.preInit();
        }
    
        public void init() {
            super.init();
        }
    
        public void postInit() {
            super.postInit();
        }
    
        @Override
        public boolean playerIsInCreativeMode(EntityPlayer player) {
            if (player instanceof EntityPlayerMP) {
                EntityPlayerMP entityPlayerMP = (EntityPlayerMP) player;
                return entityPlayerMP.theItemInWorldManager.isCreative();
            } else if (player instanceof EntityPlayerSP) {
                return Minecraft.getMinecraft().playerController.isInCreativeMode();
            }
            return false;
        }
    }
    
    • DedicatedServerProxy:继承CommonProxy,在它的基础上做一些只有server端需要处理的事情。但大部分时间不需要扩展,只要完成CommonProxy的工作就行了。
    package com.zql.mc.zmod;
    
    import net.minecraft.entity.player.EntityPlayer;
    import net.minecraft.entity.player.EntityPlayerMP;
    
    public class DedicatedServerProxy extends CommonProxy {
    
        public void preInit() {
            super.preInit();
        }
    
        public void init() {
            super.init();
        }
    
        public void postInit() {
            super.postInit();
        }
    
        @Override
        public boolean playerIsInCreativeMode(EntityPlayer player) {
            if (player instanceof EntityPlayerMP) {
                EntityPlayerMP entityPlayerMP = (EntityPlayerMP) player;
                return entityPlayerMP.theItemInWorldManager.isCreative();
            }
            return false;
        }
    }
    
    

    目前读者如果上面的代码有疑惑是正常的,等后面结合例子看的时候就明朗了。下面来看资源目录的初始化:
    在src/main/resources下新建一下几个包:

    • assets.zmod.blockstates:用于自定义方块状态的json文件存储。
    • assets.zmod.lang:用于自定义物品和方块等的名称。
    • assets.zmod.models.block:用于自定义方块模型的json文件存储。
    • assets.zmod.models.item:用于自定义物品模型的json文件存储。
    • assets.zmod.textures.blocks:用于自定义方块的纹理图片的存储。
    • assets.zmod.textures.items:用于自定义物品的纹理图片的存储。

    以上文件夹名字是固定的,不能有任何偏差。

    以上就是我们要做的准备工作,所谓工欲善其事,必先利其器。现在我们的利器已经准备完毕,接下来就可以开始我们物品和方块的自定义之旅了。

    文章中涉及的代码均在我的github中:
    Minecraft-Forge-Sample

    参考资料

    https://github.com/TheGreyGhost/MinecraftByExample

  • 相关阅读:
    linux 常用操作指令(随时更新)
    Spring @Scheduled应用解析
    H5的FormData对象完成ajax上传文件multiFile
    微服务的4个设计原则和19个解决方案
    微服务实战(六):如何做好服务拆分?
    微服务实战(五):微服务化之缓存的设计
    微服务实战(四):微服务化之无状态化与容器化
    微服务实战(三):以MySQL为例,从原理上理解那些所谓的数据库军规
    微服务实战(二):微服务的接入层设计与动静资源隔离
    微服务实战(一):微服务化的基石——持续集成
  • 原文地址:https://www.cnblogs.com/zqlxtt/p/5206479.html
Copyright © 2020-2023  润新知