Luohuayu / CatServer

高性能和高兼容性的1.12.2/1.16.5/1.18.2版本Forge+Bukkit+Spigot服务端 (A high performance and high compatibility 1.12.2/1.16.5/1.18.2 version Forge+Bukkit+Spigot server)
https://catmc.org
GNU Lesser General Public License v3.0
1.94k stars 204 forks source link

[1.18.2] 机械动力的动力锯无法将物品放入箱子 #864

Closed 1309896340 closed 2 months ago

1309896340 commented 4 months ago

运行环境

Minecraft版本: 1.18.2 构建版本: ecf9bc1 相关模组/插件: create-1.18.2-0.5.0.d https://www.curseforge.com/minecraft/mc-mods/create/files/all?page=1&pageSize=20&version=1.18.2&gameVersionTypeId=1

描述这个BUG 按照如下指南自动化树场搭建的多方块结构,无法将动力锯摧毁的木块自动放入原版箱子中,而是消失了。使用木桶容器可以正常运行,但是所有其他容器(如更多箱子mod)均会出现以上问题。 在单人模式中能正常运行,原版箱子作为容器不会导致物品消失,该问题仅出现在使用catserver运行的服务器上

导致的问题 被动力锯摧毁的物品不会掉落,且全部消失

复现方法 使用catserver创建一个无插件,仅包含create模组的服务端,并运行。配置一个客户端连接,并按照自动化树场的指南搭建即可。

i493052739 commented 4 months ago

image

不只是树场 用原版箱子作为机械动力机械结构实体(Contraption/多方块结构)的储存位,被强力胶选定的多方块区域在实体化成Contraption时,物品还不会丢失;但一旦在去实体化后(变回方块后)都会导致内部储存的所有物品丢失。

目前测试,原版箱子、双箱子、陷阱箱、Quark (asm的原版箱子)会丢失; 但原版木桶、原版熔炉、Iron Chest模组箱子、CookingForBlockHeads模组冰箱、MyCrayfishFurniture模组抽屉等,不会存在该问题。

猜测是 CatCustomInventory 相关的箱子,及 BarrelBlock 正常 原版箱子 ChestBlock 及其子类如 TrappedChestBlock,可能有地方需要修复

是否有后台报错:

简化的复现步骤:

猜测的问题触发位置: com.simibubi.create.content.contraptions.AbstractContraptionEntitydisassemble 方法 https://github.com/Creators-of-Create/Create/blob/2201d87da7744cf9ee3f83e1e4c21643244f342b/src/main/java/com/simibubi/create/content/contraptions/Contraption.java#L1076-L1098 其中的 blockEntity.load(tag);storage.addStorageToWorld(block, blockEntity);

继续追进去能够发现:addStorageToWorld 对 ChestBlockEntity 有独立的处理逻辑: https://github.com/Creators-of-Create/Create/blob/2201d87da7744cf9ee3f83e1e4c21643244f342b/src/main/java/com/simibubi/create/content/contraptions/MountedStorage.java#L143-L152 其调用 saveWithFullMetadatasaveWithoutMetadata,对应 cat 存入 PublicBukkitValuesthis.persistentDataContainer.toTagCompound() 对应 cat craftbukkit 部分: https://github.com/Luohuayu/CatServer/blob/23cd1bf070f0bdd88789ad99b54cd537a5c706a9/src/main/java/org/bukkit/craftbukkit/v1_18_R2/persistence/CraftPersistentDataContainer.java#L119-L125this.customDataTags 可能需要进一步 debug 查看这里实际的内容变动


也可能是我排查的方向错了,可能只是 craftBukkit 没存进 forge 的箱子内容导致原版箱子变空(比如假设所有craftBukkit的原版箱子 CraftInventory 在放下时默认为空箱子?或者没有 loadForgeContainer)而 CatCustomInventory 相关的容器能够正常 loadForgeContainer 顺着这个思路去看的话: https://github.com/Luohuayu/CatServer/blob/23cd1bf070f0bdd88789ad99b54cd537a5c706a9/src/main/java/catserver/server/inventory/CatCustomInventory.java#L27-L30 其中的 https://github.com/Luohuayu/CatServer/blob/23cd1bf070f0bdd88789ad99b54cd537a5c706a9/src/main/java/org/bukkit/craftbukkit/v1_18_R2/inventory/CraftInventoryCustom.java#L34-L36 能拿到 forge 的 MinecraftInventory

目前还不太会用 gradle 去 debug cat... 不过至于为什么猜是通过 ItemStackHandler 构造的 CatCustomInventory 是因为机械动力的 MountedStorage 的 handler 和 dummyHandler 成员均是 ItemStackHandler

CalenXwX commented 2 months ago

image

不只是树场 用原版箱子作为机械动力机械结构实体(Contraption/多方块结构)的储存位,被强力胶选定的多方块区域在实体化成Contraption时,物品还不会丢失;但一旦在去实体化后(变回方块后)都会导致内部储存的所有物品丢失。

目前测试,原版箱子、双箱子、陷阱箱、Quark (asm的原版箱子)会丢失; 但原版木桶、原版熔炉、Iron Chest模组箱子、CookingForBlockHeads模组冰箱、MyCrayfishFurniture模组抽屉等,不会存在该问题。

猜测是 CatCustomInventory 相关的箱子,及 BarrelBlock 正常 原版箱子 ChestBlock 及其子类如 TrappedChestBlock,可能有地方需要修复

是否有后台报错:

简化的复现步骤:

  • 放铁轨
  • 放装配站在铁轨上
  • 放矿车在装配站中
  • 放拉杆在装配站上
  • 放箱子在装配站上
  • 用强力胶黏住多个并排的箱子
  • 拉动拉杆、开关控制 contraption 和 block 之间的转换

猜测的问题触发位置: com.simibubi.create.content.contraptions.AbstractContraptionEntitydisassemble 方法 https://github.com/Creators-of-Create/Create/blob/2201d87da7744cf9ee3f83e1e4c21643244f342b/src/main/java/com/simibubi/create/content/contraptions/Contraption.java#L1076-L1098 其中的 blockEntity.load(tag);storage.addStorageToWorld(block, blockEntity);

继续追进去能够发现:addStorageToWorld 对 ChestBlockEntity 有独立的处理逻辑: https://github.com/Creators-of-Create/Create/blob/2201d87da7744cf9ee3f83e1e4c21643244f342b/src/main/java/com/simibubi/create/content/contraptions/MountedStorage.java#L143-L152 其调用 saveWithFullMetadatasaveWithoutMetadata,对应 cat 存入 PublicBukkitValuesthis.persistentDataContainer.toTagCompound() 对应 cat craftbukkit 部分:

https://github.com/Luohuayu/CatServer/blob/23cd1bf070f0bdd88789ad99b54cd537a5c706a9/src/main/java/org/bukkit/craftbukkit/v1_18_R2/persistence/CraftPersistentDataContainer.java#L119-L125

this.customDataTags 可能需要进一步 debug 查看这里实际的内容变动 也可能是我排查的方向错了,可能只是 craftBukkit 没存进 forge 的箱子内容导致原版箱子变空(比如假设所有craftBukkit的原版箱子 CraftInventory 在放下时默认为空箱子?或者没有 loadForgeContainer)而 CatCustomInventory 相关的容器能够正常 loadForgeContainer 顺着这个思路去看的话:

https://github.com/Luohuayu/CatServer/blob/23cd1bf070f0bdd88789ad99b54cd537a5c706a9/src/main/java/catserver/server/inventory/CatCustomInventory.java#L27-L30

其中的 https://github.com/Luohuayu/CatServer/blob/23cd1bf070f0bdd88789ad99b54cd537a5c706a9/src/main/java/org/bukkit/craftbukkit/v1_18_R2/inventory/CraftInventoryCustom.java#L34-L36

能拿到 forge 的 MinecraftInventory 目前还不太会用 gradle 去 debug cat... 不过至于为什么猜是通过 ItemStackHandler 构造的 CatCustomInventory 是因为机械动力的 MountedStorage 的 handler 和 dummyHandler 成员均是 ItemStackHandler

说起来调试 我也没弄明白怎么让clone下来的catserver跑起来 甚至mc本体这个依赖都下不动() 不过调试的话 可以把整个服务器目录放到一个maven项目里 用maven启动catserver那个jar文件 如果要看jar里面代码的话 把forge那几个jar添加成maven依赖 然后刷新maven 就可以看里面代码了 比如这样w

        <dependency>
            <groupId>net.minecraftforge</groupId>
            <artifactId>Forge-universal</artifactId>
            <version>1.18.2</version>
            <scope>system</scope>
            <systemPath>${project.basedir}/run/libraries/net/minecraftforge/forge/1.18.2-40.2.14/forge-1.18.2-40.2.14-universal.jar</systemPath>
        </dependency>

这个run目录里面就是服务器 (其实那次修拔刀剑capability丢失那个bug的时候 我一直靠写mod然后mixin进去打日志 内心是崩溃的QwQ) 祝你好运w