Unity游戏Mod/插件制作教程03 - 插件实例1: HelloWorld

news2025/2/28 21:37:05

准备工作
作为编程类的教程,果然第一个需要来一个传统项目——HelloWolrd。

在开始之前,我先贴一个链接,这是BepInex官方的开发手册 https://bepinex.github.io/bepinex_docs/v5.0/articles/dev_guide/index.html 有什么问题也可以翻阅官方的手册,也许会有启发。

我们打开VS,新建一个.Net Framework类库项目,Framework版本根据游戏使用的版本决定,打开游戏的Data/Managed文件夹,看看System开头的几个文件,都是使用的什么版本。

我们以【~在魔界当女仆~恶魔天使与勇者的秘密喫茶店】和【装机模拟器】这两款游戏为例,可以看到在前者中,版本为4.6,后者为3.5,大多数的情况下,我们会使用4以上的版本。 

 以【~在魔界当女仆~恶魔天使与勇者的秘密喫茶店】为例,我们新建一个.NetFramework 4.6的类库项目。

接下来我们添加一下常用的引用,我们一般会根据情况选择使用哪些dll,首先BepInex/Core文件夹下的BepInEx.dll和0Harmony20.dll是很常用的dll,我们选择上。在Data/Managed文件夹内有很多游戏使用到的dll,我举几个常用的。

Assembly-CSharp.dll //绝大多数的Unity游戏,逻辑都是放在这里的,所以想调用或者修改游戏内的东西,这个要添加引用
Assembly-CSharp-firstpass.dll //少数游戏会把逻辑放在这里,比如装机模拟器
UnityEngine.dll Unity2017之后,//各种功能都被分散成很多dll,各种dll负责转发引用,所以这个dll我们每次都加上
UnityEngine.CoreModule.dll //引擎的核心dll
UnityEngine.IMGUIModule.dll //OnGUI所使用的dll,也就是通常情况下,我们插件的界面所使用的界面库
其他的dll。我们以后使用到再说,今天只是写一个最最基本的插件。

 小技巧: 全选所有引用,把 复制本地 属性改为否,如果我们不这样选择的话,回头编译的时候,就会把引用到的相关dll也一起复制到输出目录,可能会有一大堆文件,所以这样比较简洁。

开始编写插件
我们给默认的Class1修改一个我们想要的名字,我这里改为PluginTutorial,然后将BepInEx的命名空间using一下。

在BepInEx中,给我们准备了一个类,BaseUnityPlugin,这是继承于MonoBehaviour的,也就是说,我们的插件,最终会以组件的形式挂载,实际上也是这样,每个插件最终都会挂载到游戏中BepInEx的物体身上。所以我们可以使用MonoBehaviour的各种生命周期,比如Awake,Start,Update等等,这些我们以后再说,先来看一下最基础的插件的样子。

using System;
using BepInEx;

namespace PluginTutorial
{
    //插件描述特性 分别为 插件ID 插件名字 插件版本(必须为数字)
    [BepInPlugin("me.xiaoye97.plugin.Tutorial", "Tutorial Plugin", "1.0")]
    public class PluginTutorial : BaseUnityPlugin //继承BaseUnityPlugin
    {
        //Unity的Start生命周期
        void Start()
        {
            //输出日志
            Logger.LogInfo("HelloWorld!");
        }
    }
}
我们将PluginTutorial继承BaseUnityPlugin,并在类上方添加了一个叫做BepInPlugin的特性,这是必须要完成的,只有这样才能正确加载插件。

如果你不知道特性是什么,可以去补一下C#关于特性方面的知识。

在BepInPlugin特性中,我们填入了3个参数,分别是插件的ID,插件的名字,插件的版本号,对于ID,我个人习惯使用域名反写法,一般是me.xiaoye97.plugin.游戏名.插件名,插件的名字没有什么特别的要求,直观即可。在插件版本这里,必须是数字形式的版本号,不能夹杂字母等。

这样。我们第一个插件就完成了,在顶部工具栏选择生成->生成 PluginTutorial,等生成完毕后,打开输出的目录,将生成的PluginTutorial.dll复制到我们的 BepInEx/plugins目录下。
运行游戏,通过控制台我们可以看到我们的插件已经成功加载了,虽然它现在什么功能都没有。
其他事项
插件的特性除了BepInExPlugin之外,还有两个可能会用到的特性。

第一个是BepInProcess特性,大部分情况下,我们不需要写这个特性,但是偶尔会遇到特殊情况。比如,在I社游戏(例如AI少女、恋爱活动等)中,不仅有游戏本体,还有一个工作室程序,将游戏本体与内容创作进行了分割,这样,就会有两个exe,但是,他们是两个不同的exe,有很多地方是不能公用的。那么,只需要用这个特性,就可以限制插件在指定的exe上可以运行。
例如

[BepInPlugin("me.xiaoye97.plugin.Tutorial", "Tutorial Plugin", "1.0")]
[BepInProcess("Maid In Makai.exe")]
public class PluginTutorial : BaseUnityPlugin
{

}
这样,就是限定只在这个exe中运行,如果想限制在几个exe中可以运行,就继续添加这样特性即可。

第二个是BepInDependency特性,如果我们的插件,需要以其他的什么插件为前置插件,那么就需要使用这个特性添加依赖,以保证只有在有前置插件的情况下加载我们的插件。

BepInDependency特性有3种写法,分别是

[BepInPlugin("me.xiaoye97.plugin.Tutorial", "Tutorial Plugin", "1.0")]
// 软依赖,如果没有前置插件,依旧继续加载
[BepInDependency("com.bepinex.plugin.somedependency", BepInDependency.DependencyFlags.SoftDependency)]
// 硬依赖,如果没有前置插件,则停止加载
[BepInDependency("com.bepinex.plugin.importantdependency", BepInDependency.DependencyFlags.HardDependency)]
// 省略参数,则默认为硬依赖
[BepInDependency("com.bepinex.plugin.anotherimportantone")]
public class PluginTutorial : BaseUnityPlugin
{

}

除了这些特性之外,还有一点我们需要注意的是,一个dll中可以包括多个插件,只要我们写多个继承BaseUnityPlugin的类,并为他们赋予BepInPlugin特性即可。


有什么问题或者建议可以在评论区评论或者与我私信交流。 作者:宵夜97 https://www.bilibili.com/read/cv8997577?spm_id_from=333.999.0.0 出处:bilibili

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/24443.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

论文阅读【6】RRN:LSTM论文阅读报告(1)

lstm类似于Simple_RNN,但是又比他复杂很多.我是参考这个视频的老师讲解的,这个老师讲解的非常好.https://www.bilibili.com/video/BV1FP4y1Z7Fj?p4&vd_source0a7fa919fba05ffcb79b57040ef74756 lstm的最重要的设计就是那一条传输带,即为向量CtC_tCt​,过去的信息通过他传送…

跨程序共享数据:Android四大组件之内容提供器

跨程序共享数据:Android四大组件之内容提供器前言七、跨程序共享数据:Android四大组件之内容提供器7.1 内容提供器(Content Provider)简介7.2 运行时权限(软件不能为所欲为,想要什么权限,还得主…

【project 】软件使用

project软件使用 1.如何为某任务或资源创建日历 创建新日历 工具->更改工作时间->新建->定义日历名称,选择“新建基准日历”->根据各承建商的日历创建相应的日历 使用新日历 拷贝各承建商的各项任务到指定的项目计划中,然后&#xff…

基于特征选择的二元蜻蜓算法(Matlab代码实现)

🍒🍒🍒欢迎关注🌈🌈🌈 📝个人主页:我爱Matlab 👍点赞➕评论➕收藏 养成习惯(一键三连)🌻🌻🌻 🍌希…

C. String Equality(思维)

Problem - 1451C - Codeforces Ashish有两个字符串a和b,每个字符串的长度为n,还有一个整数k。 他想通过对a进行一些(可能是零)操作,将字符串a转换成字符串b。 在一次操作中,他可以 选择一个索引i&#x…

哪吒汽车的技术发布会都发布了什么?纯干货抢先看

11月21日,哪吒汽车发布了浩智超算、浩智电驱、浩智增程三大技术品牌,并推出三款技术产品,包括智能汽车中央超算平台、800V SiC高性能电驱系统、高效三合一增程器。去年年底,哪吒曾经发布过山海平台,据说是一个支持哪吒…

性能环境搭建(0-CentOS7 安装配置)

1.前言 根据现有的组件,准备动手搭建一套完整的监控环境。既然是练手,还是在虚拟机里自己先练习一下。出了问题也好恢复。所有就先从最基本的开始。那就是操作系统开始搭建玩起来。 2.环境 资源有效利用吧,公司的资源能自由使用的那最方便…

数据结构-复杂度(一)

目录 一、什么是复杂度? 算法效率: 复杂度: 二、复杂度分类 一、时间复杂度 二、空间复杂度(Space Complexity) 了解数据结构之前需要了解复杂度。 一、什么是复杂度? 在介绍复杂度之前我们现分享一…

CengBox靶机

0x01 信息收集 nmap -sV 10.0.2.6 22 ssh端口,弱口令爆破为主 80 web页面 目录遍历,备份文件查找等 dirsearch -u http://10.0.2.6 获取了目录,发现存在一个maseradmin目录,可能存在些东西,继续扫。 dirsearch -u …

C规范编辑笔记(四)

大家好,今天来给大家分享一下C规范编辑笔记第四篇,距离我们C规范编辑笔记第三篇也快过去了一个月,这次继续分享一波~ 1、以大写形式声明常量, 为避免误解,常量值必须根据其类型使用后缀。这不仅有助于代码阅读&#x…

CSO面对面丨如何通过“联合作战”,加强银行安全体系建设

随着数字化转型的深入,以银行为代表的金融机构不断加码金融科技建设。然而随着线上业务量不断上升,银行面临的安全风险暴露面也愈大、问题愈加复杂。本期腾讯安全《CSO面对面》栏目,邀请到某头部商业银行安全主管,以金融行业的安全…

【Lilishop商城】No1-1.业务了解+划分各模块逻辑

目录 A1.整体业务逻辑 B1.模块整理 C1.运营后台 C2.店铺后台 C3.买方平台 B2.重点模块梳理图 C1.订单模块 C2.退货/退款模块(即售后模块) C3.促销活动模块 A2.模块划分(自己思考的) A3.数据结构划分(自己思考…

算法设计与分析 SCAU11079 可以移动的石子合并(优先做)

11079 可以移动的石子合并(优先做) 时间限制:1000MS 代码长度限制:10KB 提交次数:25 通过次数:9 题型: 编程题 语言: G;GCC;VC;JAVA Description 有n堆石子形成一行(a1,a2,…,an,ai为第i堆石子个数),现要将石子合并成一堆&…

Android App开发手机阅读中贝塞尔曲线的原理讲解及实现波浪起伏动画实战(附源码和演示视频 可直接使用)

需要图片集和源码请点赞关注收藏后评论区留言~~~ 一、贝塞尔曲线的原理 贝塞尔曲线是一种用于二维图形的数学曲线。贝塞尔曲线由节点和线段构成,其中节点是可拖动的支点,而线段彷佛有弹性的牛皮筋。它除了起点和终点之外,不再描绘中间的折现…

嵌入式(驱动开发)(中断处理)

一、什么是中断 一种硬件上的通知机制,用来通知CPU发生了某种需要立即处理的事件 分为: 内部中断 CPU执行程序的过程中,发生的一些硬件出错、运算出错事件(如分母为0、溢出等等),不可屏蔽外部中断 外设发…

SpringBoot怎么整合第三方缓存技术/EhCache缓存技术使用以及Redis缓存技术使用怎么在SpringBoot中使用

写在前面: 继续记录自己的SpringBoot学习之旅,这次是SpringBoot应用相关知识学习记录。若看不懂则建议先看前几篇博客,详细代码可在我的Gitee仓库SpringBoot克隆下载学习使用! 3.5 整合第三方技术 3.5.1 缓存 3.5.1.1 介绍 缓…

2022/11/21[指针] 多维数组与指针的联系

1、指向数组元素的指针变量 #include<stdio.h> int main() {int* p;int a[3][4] { {1,2,3,4},{5,6,7,8},{9,10,11,12} };int i, j;//将第0行第0列的地址赋给pfor (p a[0]; p < a[0] 12; p)//注意是a[0]{if ((p - a[0]) % 4 0)printf("\n");printf("…

java--Lambda(2)表达式语法

文章目录0 写在前面1 Lambda 表达式的五种形式1.1 不包含参数&#xff1a;1.2 包含一个参数&#xff1a;1.3 有多个参数1.4 表达式主体是不是一个代码块1.5 不声明参数类型2 写在末尾0 写在前面 最基本的 Lambda 表达式&#xff0c;它由三部分组成具体格式是这样子的&#xff…

【Py】使用flask-apscheduler动态调整作业参数(附源码)

之前的项目常使用Apscheduler进行定时任务调度&#xff0c;但最近想通过接口对这些任务进行动态调整&#xff0c;比如调整任务启停、调整任务执行时间、间隔时间等等 flask-apscheduler这个基于flask的库能够满足上面的需求&#xff0c;而且由于基于flask&#xff0c;所以我常…

查题校园免费题库接口

查题校园免费题库接口 本平台优点&#xff1a; 多题库查题、独立后台、响应速度快、全网平台可查、功能最全&#xff01; 1.想要给自己的公众号获得查题接口&#xff0c;只需要两步&#xff01; 2.题库&#xff1a; 查题校园题库&#xff1a;查题校园题库后台&#xff08;点…