伪方块
intermediate
有时您的方块需要实现Minecraft原生不支持的功能。一个可行的解决方案是创建能模拟方块特性的实体。
创建碰撞体
固体实体教程介绍了四种创建碰撞体的方法,涉及runtime_identifiers、方块和组件等不同技术。
基础组件
以下组件是使实体具备方块行为的关键。注意不要添加"minecraft:physics": {}组件,否则实体会下坠或与水/岩浆等方块发生异常碰撞。
BP/entities/your_entity.json#minecraft:entity/components
json
{
// 击退抗性确保实体不会被其他生物撞离原位
"minecraft:knockback_resistance": {
"value": 1
},
// 控制实体是否可被推动
"minecraft:pushable": {
"is_pushable": false,
"is_pushable_by_piston": true
},
// 设置实体可推动其他实体的距离
"minecraft:push_through": {
"value": 1
},
// 使实体无敌
"minecraft:damage_sensor": {
"triggers": [
{
"deals_damage": false,
"cause": "all"
}
]
}
}实体旋转对齐
需要通过数学计算实现实体旋转对齐:
json
"rotation": [ 0, "-q.body_y_rotation + (Math.round(q.body_y_rotation / 90) * 90)", 0 ]将此代码应用于模型核心文件夹(包含其他组件的文件夹)的动画中,确保X轴和Z轴枢轴点为0以避免视觉错误。同时不要添加以下组件:
"minecraft:behavior.look_at_entity": {}"minecraft:behavior.look_at_player": {}"minecraft:behavior.look_at_target": {}
因为这些组件会改变目标Y轴旋转,进而影响身体Y轴旋转导致模型移动。同样不要添加行走类组件。
实体位置对齐
位置对齐的实现更为复杂:
首先在minecraft:entity_spawned事件中,通过queue_command创建临时方块,并生成一个带转换事件的虚拟实体,避免重复触发生成事件。
BP/entities/your_entity.json#minecraft:entity/events
json
// 原实体中的事件
"minecraft:entity_spawned": {
"add": {
"components_groups": [
"despawn" // 需要同时移除初始实体
]
},
"queue_command": {
"command": ["setblock ~~~ wiki:align"]
}
}BP/entities/your_entity.json#minecraft:entity/component_groups
json
// 原实体中的组件组
"component_groups": {
"despawn": {
"minecraft:despawn": {}
}
}用于在方块中心生成虚拟实体的特殊方块:
BP/blocks/your_dummy_block.json
json
{
"format_version": "1.21.70",
"minecraft:block": {
"description": {
"identifier": "wiki:align"
},
"components": {
"minecraft:light_dampening": 0,
"minecraft:collision_box": false,
"minecraft:selection_box": false,
"minecraft:loot": "loot_tables/empty.json",
"minecraft:geometry": "geometry.empty",
"minecraft:material_instances": {
"*": {
"texture": "wiki:empty"
}
},
"minecraft:destructible_by_mining": {
"seconds_to_destroy": 2
},
"minecraft:custom_components": ["wiki:align_entity"]
}
}
}自定义组件脚本将利用beforeOnPlayerPlace事件来阻止方块放置并生成实体:
js
import { world } from "@minecraft/server";
/** @type {import("@minecraft/server").BlockCustomComponent} */
const BlockAlignEntityComponent = {
beforeOnPlayerPlace(event) {
event.cancel = true;
const location = event.block.center();
event.dimension.spawnEntity("wiki:dummy_align", location);
},
};
world.beforeEvents.worldInitialize.subscribe(({ blockComponentRegistry }) => {
blockComponentRegistry.registerCustomComponent("wiki:align_entity", BlockAlignEntityComponent);
});BP/entities/your_dummy_entity.json
json
{
"format_version": "1.13.0",
"minecraft:entity": {
"description": {
"identifier": "wiki:dummy_align", // 虚拟实体用于避免触发原实体的生成事件
"is_spawnable": false,
"is_summonable": true,
"is_experimental": false
},
"component_groups": {
"transform": {
"minecraft:transformation": {
"into": "wiki:your_entity",
"delay": 0
}
}
},
"components": {
"minecraft:physics": {
"has_gravity": false
},
"minecraft:collision_box": {
"width": 0.1,
"height": 0.1
},
"minecraft:damage_sensor": {
"triggers": {
"cause": "all",
"deals_damage": false
}
}
},
"events": {
"minecraft:entity_spawned": {
"add": {
"component_groups": ["transform"]
}
}
}
}
}破损纹理效果
原版方块在被破坏时会显示裂纹纹理。以下是如何为实体添加此效果:
首先在实体文件中添加纹理,建议直接使用原版纹理以保证资源包兼容性:
RP/entity/your_entity.json#description
json
{
"textures": {
"default": "textures/entity/your_texture",
"destroy_stage_0": "textures/environment/destroy_stage_0",
"destroy_stage_1": "textures/environment/destroy_stage_1",
"destroy_stage_2": "textures/environment/destroy_stage_2",
"destroy_stage_3": "textures/environment/destroy_stage_3",
"destroy_stage_4": "textures/environment/destroy_stage_4",
"destroy_stage_5": "textures/environment/destroy_stage_5",
"destroy_stage_6": "textures/environment/destroy_stage_6",
"destroy_stage_7": "textures/environment/destroy_stage_7",
"destroy_stage_8": "textures/environment/destroy_stage_8",
"destroy_stage_9": "textures/environment/destroy_stage_9"
}
}添加一个所有立方体都膨胀0.1的几何体以避免Z轴冲突:
RP/entity/your_entity.json#description
json
{
"geometry": {
"default": "geometry.your_geometry",
"broken": "geometry.broken"
}
}最后添加新的渲染控制器来选择不同破损阶段的纹理(注意保留原有控制器):
RP/render_controllers/my_entity.json
json
{
"controller.render.broken": {
"arrays": {
"textures": {
"array.broken": [
"texture.destroy_stage_9",
"texture.destroy_stage_8",
"texture.destroy_stage_7",
"texture.destroy_stage_6",
"texture.destroy_stage_5",
"texture.destroy_stage_4",
"texture.destroy_stage_3",
"texture.destroy_stage_2",
"texture.destroy_stage_1",
"texture.destroy_stage_0",
"texture.normal"
]
}
},
"geometry": "Geometry.broken",
"materials": [
{
"*": "Material.default"
}
],
"textures": [
// 根据实体生命值计算纹理阶段:10生命值保持原式,20生命值改为0.5,40生命值改为0.25...
"array.broken[q.health * 1]"
]
}
}






