mirror of
https://git.minetest.land/VoxeLibre/VoxeLibre.git
synced 2024-11-25 20:11:06 +01:00
Merge pull request 'Add api and following mobs as starers: cow, chicken, creeper, pig, sheep, skellys. spider, villager, villager_zombie, wolf' (#2716) from new_mobs_look_at_players into master
Reviewed-on: https://git.minetest.land/MineClone2/MineClone2/pulls/2716 Reviewed-by: cora <cora@noreply.git.minetest.land> Reviewed-by: 𝕵𝖔𝖍𝖆𝖓𝖓𝖊𝖘 𝕱𝖗𝖎𝖙𝖟 <mrrar@noreply.git.minetest.land>
This commit is contained in:
commit
3aaf0f3e29
42 changed files with 296 additions and 116 deletions
|
@ -610,3 +610,95 @@ function mcl_util.get_pointed_thing(player, liquid)
|
|||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- This following part is 2 wrapper functions + helpers for
|
||||
-- object:set_bones
|
||||
-- and player:set_properties preventing them from being resent on
|
||||
-- every globalstep when they have not changed.
|
||||
|
||||
local function roundN(n, d)
|
||||
if type(n) ~= "number" then return n end
|
||||
local m = 10^d
|
||||
return math.floor(n * m + 0.5) / m
|
||||
end
|
||||
|
||||
local function close_enough(a,b)
|
||||
local rt=true
|
||||
if type(a) == "table" and type(b) == "table" then
|
||||
for k,v in pairs(a) do
|
||||
if roundN(v,2) ~= roundN(b[k],2) then
|
||||
rt=false
|
||||
break
|
||||
end
|
||||
end
|
||||
else
|
||||
rt = roundN(a,2) == roundN(b,2)
|
||||
end
|
||||
return rt
|
||||
end
|
||||
|
||||
local function props_changed(props,oldprops)
|
||||
local changed=false
|
||||
local p={}
|
||||
for k,v in pairs(props) do
|
||||
if not close_enough(v,oldprops[k]) then
|
||||
p[k]=v
|
||||
changed=true
|
||||
end
|
||||
end
|
||||
return changed,p
|
||||
end
|
||||
|
||||
--tests for roundN
|
||||
local test_round1=15
|
||||
local test_round2=15.00199999999
|
||||
local test_round3=15.00111111
|
||||
local test_round4=15.00999999
|
||||
|
||||
assert(roundN(test_round1,2)==roundN(test_round1,2))
|
||||
assert(roundN(test_round1,2)==roundN(test_round2,2))
|
||||
assert(roundN(test_round1,2)==roundN(test_round3,2))
|
||||
assert(roundN(test_round1,2)~=roundN(test_round4,2))
|
||||
|
||||
-- tests for close_enough
|
||||
local test_cb = {-0.35,0,-0.35,0.35,0.8,0.35} --collisionboxes
|
||||
local test_cb_close = {-0.351213,0,-0.35,0.35,0.8,0.351212}
|
||||
local test_cb_diff = {-0.35,0,-1.35,0.35,0.8,0.35}
|
||||
|
||||
local test_eh = 1.65 --eye height
|
||||
local test_eh_close = 1.65123123
|
||||
local test_eh_diff = 1.35
|
||||
|
||||
local test_nt = { r = 225, b = 225, a = 225, g = 225 } --nametag
|
||||
local test_nt_diff = { r = 225, b = 225, a = 0, g = 225 }
|
||||
|
||||
assert(close_enough(test_cb,test_cb_close))
|
||||
assert(not close_enough(test_cb,test_cb_diff))
|
||||
assert(close_enough(test_eh,test_eh_close))
|
||||
assert(not close_enough(test_eh,test_eh_diff))
|
||||
assert(not close_enough(test_nt,test_nt_diff)) --no floats involved here
|
||||
|
||||
--tests for properties_changed
|
||||
local test_properties_set1={collisionbox = {-0.35,0,-0.35,0.35,0.8,0.35}, eye_height = 0.65, nametag_color = { r = 225, b = 225, a = 225, g = 225 }}
|
||||
local test_properties_set2={collisionbox = {-0.35,0,-0.35,0.35,0.8,0.35}, eye_height = 1.35, nametag_color = { r = 225, b = 225, a = 225, g = 225 }}
|
||||
|
||||
local test_p1,_=props_changed(test_properties_set1,test_properties_set1)
|
||||
local test_p2,_=props_changed(test_properties_set1,test_properties_set2)
|
||||
|
||||
assert(not test_p1)
|
||||
assert(test_p2)
|
||||
|
||||
function mcl_util.set_properties(obj,props)
|
||||
local changed,p=props_changed(props,obj:get_properties())
|
||||
if changed then
|
||||
obj:set_properties(p)
|
||||
end
|
||||
end
|
||||
|
||||
function mcl_util.set_bone_position(obj,b,p,r) --bone,position,rotation
|
||||
local oldp,oldr=obj:get_bone_position(b)
|
||||
if vector.equals(vector.round(oldp),vector.round(p)) and vector.equals(vector.round(oldr),vector.round(r)) then
|
||||
return
|
||||
end
|
||||
obj:set_bone_position(b,p,r)
|
||||
end
|
||||
|
|
|
@ -61,6 +61,13 @@ if minetest.settings:get_bool("only_peaceful_mobs", false) then
|
|||
end)
|
||||
end
|
||||
|
||||
|
||||
local function dir_to_pitch(dir)
|
||||
--local dir2 = vector.normalize(dir)
|
||||
local xz = math.abs(dir.x) + math.abs(dir.z)
|
||||
return -math.atan2(-dir.y, xz)
|
||||
end
|
||||
|
||||
-- pathfinding settings
|
||||
local enable_pathfinding = true
|
||||
local stuck_timeout = 3 -- how long before mob gets stuck in place and starts searching
|
||||
|
@ -3706,6 +3713,63 @@ local mob_step = function(self, dtime)
|
|||
|
||||
-- end rotation
|
||||
|
||||
if self.head_swivel and type(self.head_swivel) == "string" then
|
||||
local oldp,oldr = self.object:get_bone_position(self.head_swivel)
|
||||
|
||||
for _, obj in pairs(minetest.get_objects_inside_radius(pos, 10)) do
|
||||
if obj:is_player() and not self.attack or obj:get_luaentity() and obj:get_luaentity().name == self.name and self ~= obj:get_luaentity() then
|
||||
if not self._locked_object then
|
||||
if math.random(5000/self.curiosity) == 1 then
|
||||
self._locked_object = obj
|
||||
end
|
||||
else
|
||||
if math.random(10000/self.curiosity) == 1 then
|
||||
self._locked_object = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if self.attack then
|
||||
self._locked_object = self.attack
|
||||
end
|
||||
|
||||
if self._locked_object and (self._locked_object:is_player() or self._locked_object:get_luaentity()) and self._locked_object:get_hp() > 0 then
|
||||
local _locked_object_eye_height = 1.5
|
||||
if self._locked_object:get_luaentity() then
|
||||
_locked_object_eye_height = self._locked_object:get_luaentity().head_eye_height
|
||||
end
|
||||
if self._locked_object:is_player() then
|
||||
_locked_object_eye_height = self._locked_object:get_properties().eye_height
|
||||
end
|
||||
local self_rot = self.object:get_rotation()
|
||||
local player_pos = self._locked_object:get_pos()
|
||||
local direction_player = vector.direction(vector.add(self.object:get_pos(), vector.new(0, self.head_eye_height*.7, 0)), vector.add(player_pos, vector.new(0, _locked_object_eye_height, 0)))
|
||||
local mob_yaw = math.deg(-(-(self_rot.y)-(-minetest.dir_to_yaw(direction_player))))+self.head_yaw_offset
|
||||
local mob_pitch = math.deg(-dir_to_pitch(direction_player))*self.head_pitch_multiplier
|
||||
if (mob_yaw < -60 or mob_yaw > 60) and not (self.attack and self.type == "monster") then
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.multiply(oldr, 0.9))
|
||||
elseif self.attack and self.type == "monster" then
|
||||
if self.head_yaw == "y" then
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.new(mob_pitch, mob_yaw, 0))
|
||||
elseif self.head_yaw == "z" then
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.new(mob_pitch, 0, -mob_yaw))
|
||||
end
|
||||
else
|
||||
if self.head_yaw == "y" then
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.new(((mob_pitch-oldr.x)*.3)+oldr.x, ((mob_yaw-oldr.y)*.3)+oldr.y, 0))
|
||||
elseif self.head_yaw == "z" then
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.new(((mob_pitch-oldr.x)*.3)+oldr.x, 0, -(((mob_yaw-oldr.y)*.3)+oldr.y)*3))
|
||||
end
|
||||
end
|
||||
elseif not self._locked_object and math.abs(oldr.y) > 3 and math.abs(oldr.x) < 3 then
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.multiply(oldr, 0.9))
|
||||
else
|
||||
mcl_util.set_bone_position(self.object,self.head_swivel, vector.new(0,self.bone_eye_height,self.horrizonatal_head_height), vector.new(0,0,0))
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
-- run custom function (defined in mob lua file)
|
||||
if self.do_custom then
|
||||
|
||||
|
@ -3946,6 +4010,14 @@ end
|
|||
minetest.register_entity(name, {
|
||||
|
||||
use_texture_alpha = def.use_texture_alpha,
|
||||
head_swivel = def.head_swivel or nil, -- bool to activate this function
|
||||
head_yaw_offset = def.head_yaw_offset or 0, -- for wonkey model bones
|
||||
head_pitch_multiplier = def.head_pitch_multiplier or 1, --for inverted pitch
|
||||
bone_eye_height = def.bone_eye_height or 1.4, -- head bone offset
|
||||
head_eye_height = def.head_eye_height or def.bone_eye_height or 0, -- how hight aproximatly the mobs head is fromm the ground to tell the mob how high to look up at the player
|
||||
curiosity = def.curiosity or 1, -- how often mob will look at player on idle
|
||||
head_yaw = def.head_yaw or "y", -- axis to rotate head on
|
||||
horrizonatal_head_height = def.horrizonatal_head_height or 0,
|
||||
stepheight = def.stepheight or 0.6,
|
||||
name = name,
|
||||
description = def.description,
|
||||
|
|
|
@ -26,6 +26,12 @@ mcl_mobs:register_mob("mobs_mc:blaze", {
|
|||
rotate = -180,
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_blaze.b3d",
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 4,
|
||||
head_eye_height = 3.5,
|
||||
curiosity = 10,
|
||||
head_yaw_offset = 180,
|
||||
head_pitch_multiplier=-1,
|
||||
textures = {
|
||||
{"mobs_mc_blaze.png"},
|
||||
},
|
||||
|
|
|
@ -20,6 +20,13 @@ mcl_mobs:register_mob("mobs_mc:chicken", {
|
|||
collisionbox = {-0.2, -0.01, -0.2, 0.2, 0.69, 0.2},
|
||||
runaway = true,
|
||||
floats = 1,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 4,
|
||||
head_eye_height = 1.5,
|
||||
horrizonatal_head_height = -.3,
|
||||
curiosity = 10,
|
||||
head_yaw="z",
|
||||
visual_size = {x=1,y=1},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_chicken.b3d",
|
||||
textures = {
|
||||
|
|
|
@ -17,6 +17,12 @@ local cow_def = {
|
|||
"mobs_mc_cow.png",
|
||||
"blank.png",
|
||||
}, },
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 10,
|
||||
head_eye_height = 1.1,
|
||||
horrizonatal_head_height=-1.8,
|
||||
curiosity = 2,
|
||||
head_yaw="z",
|
||||
makes_footstep_sound = true,
|
||||
walk_velocity = 1,
|
||||
drops = {
|
||||
|
|
|
@ -21,6 +21,9 @@ mcl_mobs:register_mob("mobs_mc:creeper", {
|
|||
pathfinding = 1,
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_creeper.b3d",
|
||||
head_swivel = "Head_Control",
|
||||
bone_eye_height = 2.35,
|
||||
curiosity = 2,
|
||||
textures = {
|
||||
{"mobs_mc_creeper.png",
|
||||
"mobs_mc_empty.png"},
|
||||
|
|
|
@ -263,8 +263,8 @@ mcl_mobs:register_mob("mobs_mc:enderman", {
|
|||
end
|
||||
end
|
||||
if not spider_eyes then
|
||||
minetest.add_entity(self.object:get_pos(), "mobs_mc:ender_eyes"):set_attach(self.object, "head.low", vector.new(0,3.25,-1.98), vector.new(90,0,180))
|
||||
minetest.add_entity(self.object:get_pos(), "mobs_mc:ender_eyes"):set_attach(self.object, "head.low", vector.new(1,3.25,-1.98), vector.new(90,0,180))
|
||||
minetest.add_entity(self.object:get_pos(), "mobs_mc:ender_eyes"):set_attach(self.object, "head.top", vector.new(0,2.54,-1.99), vector.new(90,0,180))
|
||||
minetest.add_entity(self.object:get_pos(), "mobs_mc:ender_eyes"):set_attach(self.object, "head.top", vector.new(1,2.54,-1.99), vector.new(90,0,180))
|
||||
end
|
||||
end,
|
||||
sounds = {
|
||||
|
|
|
@ -22,6 +22,9 @@ mcl_mobs:register_mob("mobs_mc:iron_golem", {
|
|||
collisionbox = {-0.7, -0.01, -0.7, 0.7, 2.69, 0.7},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_iron_golem.b3d",
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 3.38,
|
||||
curiosity = 10,
|
||||
textures = {
|
||||
{"mobs_mc_iron_golem.png"},
|
||||
},
|
||||
|
|
|
@ -58,6 +58,14 @@ mcl_mobs:register_mob("mobs_mc:llama", {
|
|||
shoot_offset = 1, --3.5 *would* be a good value visually but it somehow messes with the projectiles trajectory
|
||||
spawn_in_group_min = 4,
|
||||
spawn_in_group = 6,
|
||||
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 11,
|
||||
head_eye_height = 3,
|
||||
horrizonatal_head_height=0,
|
||||
curiosity = 60,
|
||||
head_yaw = "z",
|
||||
|
||||
hp_min = 15,
|
||||
hp_max = 30,
|
||||
xp_min = 1,
|
||||
|
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -36,6 +36,12 @@ local ocelot = {
|
|||
hp_max = 10,
|
||||
xp_min = 1,
|
||||
xp_max = 3,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 6.2,
|
||||
head_eye_height = 0.4,
|
||||
horrizonatal_head_height=-0,
|
||||
head_yaw="z",
|
||||
curiosity = 4,
|
||||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 0.69, 0.3},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_cat.b3d",
|
||||
|
|
|
@ -135,6 +135,10 @@ mcl_mobs:register_mob("mobs_mc:parrot", {
|
|||
hp_max = 6,
|
||||
xp_min = 1,
|
||||
xp_max = 3,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 1.1,
|
||||
horrizonatal_head_height=0,
|
||||
curiosity = 10,
|
||||
collisionbox = {-0.25, -0.01, -0.25, 0.25, 0.89, 0.25},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_parrot.b3d",
|
||||
|
|
|
@ -18,6 +18,12 @@ mcl_mobs:register_mob("mobs_mc:pig", {
|
|||
"mobs_mc_pig.png", -- base
|
||||
"blank.png", -- saddle
|
||||
}},
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 7.5,
|
||||
head_eye_height = 0.8,
|
||||
horrizonatal_head_height=-1,
|
||||
curiosity = 3,
|
||||
head_yaw="z",
|
||||
makes_footstep_sound = true,
|
||||
walk_velocity = 1,
|
||||
run_velocity = 3,
|
||||
|
|
|
@ -24,6 +24,12 @@ mcl_mobs:register_mob("mobs_mc:polar_bear", {
|
|||
textures = {
|
||||
{"mobs_mc_polarbear.png"},
|
||||
},
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 2.6,
|
||||
head_eye_height = 1,
|
||||
horrizonatal_head_height = 0,
|
||||
curiosity = 20,
|
||||
head_yaw="z",
|
||||
visual_size = {x=3.0, y=3.0},
|
||||
makes_footstep_sound = true,
|
||||
damage = 6,
|
||||
|
|
|
@ -15,7 +15,12 @@ local rabbit = {
|
|||
xp_min = 1,
|
||||
xp_max = 3,
|
||||
collisionbox = {-0.2, -0.01, -0.2, 0.2, 0.49, 0.2},
|
||||
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 2,
|
||||
head_eye_height = 0.5,
|
||||
horrizonatal_head_height = -.3,
|
||||
curiosity = 20,
|
||||
head_yaw="z",
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_rabbit.b3d",
|
||||
textures = {
|
||||
|
|
|
@ -61,7 +61,12 @@ mcl_mobs:register_mob("mobs_mc:sheep", {
|
|||
xp_min = 1,
|
||||
xp_max = 3,
|
||||
collisionbox = {-0.45, -0.01, -0.45, 0.45, 1.29, 0.45},
|
||||
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 3.3,
|
||||
head_eye_height = 1.1,
|
||||
horrizonatal_head_height=-.7,
|
||||
curiosity = 6,
|
||||
head_yaw="z",
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_sheepfur.b3d",
|
||||
textures = { sheep_texture("unicolor_white") },
|
||||
|
|
|
@ -25,6 +25,9 @@ local skeleton = {
|
|||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 1.98, 0.3},
|
||||
pathfinding = 1,
|
||||
group_attack = true,
|
||||
head_swivel = "Head_Control",
|
||||
bone_eye_height = 2.38,
|
||||
curiosity = 6,
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_skeleton.b3d",
|
||||
textures = { {
|
||||
|
|
|
@ -24,11 +24,14 @@ mcl_mobs:register_mob("mobs_mc:witherskeleton", {
|
|||
collisionbox = {-0.35, -0.01, -0.35, 0.35, 2.39, 0.35},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_witherskeleton.b3d",
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 2.38,
|
||||
curiosity = 60,
|
||||
textures = {
|
||||
{
|
||||
"mobs_mc_empty.png", -- armor
|
||||
"mobs_mc_wither_skeleton.png", -- wither skeleton
|
||||
"default_tool_stonesword.png", -- sword
|
||||
"mobs_mc_wither_skeleton.png", -- wither skeleton
|
||||
}
|
||||
},
|
||||
visual_size = {x=1.2, y=1.2},
|
||||
|
|
|
@ -55,6 +55,10 @@ local spider = {
|
|||
minetest.add_entity(self.object:get_pos(), "mobs_mc:spider_eyes"):set_attach(self.object, "body.head", vector.new(0,-0.98,2), vector.new(90,180,180))
|
||||
end
|
||||
end,
|
||||
head_swivel = "Head_Control",
|
||||
bone_eye_height = 1,
|
||||
curiosity = 10,
|
||||
head_yaw="z",
|
||||
collisionbox = {-0.7, -0.01, -0.7, 0.7, 0.89, 0.7},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_spider.b3d",
|
||||
|
|
|
@ -1235,6 +1235,10 @@ mcl_mobs:register_mob("mobs_mc:villager", {
|
|||
spawn_class = "passive",
|
||||
hp_min = 20,
|
||||
hp_max = 20,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 6.3,
|
||||
head_eye_height = 2.2,
|
||||
curiosity = 10,
|
||||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 1.94, 0.3},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_villager.b3d",
|
||||
|
|
|
@ -21,6 +21,10 @@ mcl_mobs:register_mob("mobs_mc:evoker", {
|
|||
hp_max = 24,
|
||||
xp_min = 10,
|
||||
xp_max = 10,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 6.3,
|
||||
head_eye_height = 2.2,
|
||||
curiosity = 10,
|
||||
collisionbox = {-0.4, -0.01, -0.4, 0.4, 1.95, 0.4},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_villager.b3d",
|
||||
|
|
|
@ -33,6 +33,10 @@ mcl_mobs:register_mob("mobs_mc:illusioner", {
|
|||
"mobs_mc_illusionist.png", --hat
|
||||
"mcl_bows_bow.png",
|
||||
}, },
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 2.2,
|
||||
head_eye_height = 2.2,
|
||||
curiosity = 10,
|
||||
sounds = {
|
||||
-- TODO: more sounds
|
||||
distance = 16,
|
||||
|
|
|
@ -23,14 +23,18 @@ mcl_mobs:register_mob("mobs_mc:vindicator", {
|
|||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 1.94, 0.3},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_vindicator.b3d",
|
||||
textures = {
|
||||
{
|
||||
"mobs_mc_vindicator.png",
|
||||
"blank.png", --no hat
|
||||
"default_tool_steelaxe.png",
|
||||
-- TODO: Glow when attacking (mobs_mc_vindicator.png)
|
||||
},
|
||||
},
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 2.2,
|
||||
head_eye_height = 2.2,
|
||||
curiosity = 10,
|
||||
textures = {
|
||||
{
|
||||
"mobs_mc_vindicator.png",
|
||||
"blank.png", --no hat
|
||||
"default_tool_steelaxe.png",
|
||||
-- TODO: Glow when attacking (mobs_mc_vindicator.png)
|
||||
},
|
||||
},
|
||||
visual_size = {x=2.75, y=2.75},
|
||||
makes_footstep_sound = true,
|
||||
damage = 13,
|
||||
|
|
|
@ -39,13 +39,16 @@ mcl_mobs:register_mob("mobs_mc:villager_zombie", {
|
|||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 1.94, 0.3},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_villager_zombie.b3d",
|
||||
head_swivel = "Head_Control",
|
||||
bone_eye_height = 2.35,
|
||||
curiosity = 2,
|
||||
textures = {
|
||||
{"mobs_mc_empty.png", "mobs_mc_zombie_butcher.png", "mobs_mc_empty.png"},
|
||||
{"mobs_mc_empty.png", "mobs_mc_zombie_farmer.png", "mobs_mc_empty.png"},
|
||||
{"mobs_mc_empty.png", "mobs_mc_zombie_librarian.png", "mobs_mc_empty.png"},
|
||||
{"mobs_mc_empty.png", "mobs_mc_zombie_priest.png", "mobs_mc_empty.png"},
|
||||
{"mobs_mc_empty.png", "mobs_mc_zombie_smith.png", "mobs_mc_empty.png"},
|
||||
{"mobs_mc_empty.png", "mobs_mc_zombie_villager.png", "mobs_mc_empty.png"},
|
||||
{"mobs_mc_zombie_butcher.png"},
|
||||
{"mobs_mc_zombie_farmer.png"},
|
||||
{"mobs_mc_zombie_librarian.png"},
|
||||
{"mobs_mc_zombie_priest.png"},
|
||||
{"mobs_mc_zombie_smith.png"},
|
||||
{"mobs_mc_zombie_villager.png"},
|
||||
},
|
||||
visual_size = {x=2.75, y=2.75},
|
||||
makes_footstep_sound = true,
|
||||
|
|
|
@ -26,6 +26,12 @@ local wolf = {
|
|||
{"mobs_mc_wolf.png"},
|
||||
},
|
||||
makes_footstep_sound = true,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 3.5,
|
||||
head_eye_height = 1.1,
|
||||
horrizonatal_head_height=0,
|
||||
curiosity = 3,
|
||||
head_yaw="z",
|
||||
sounds = {
|
||||
attack = "mobs_mc_wolf_bark",
|
||||
war_cry = "mobs_mc_wolf_growl",
|
||||
|
|
|
@ -53,6 +53,11 @@ local zombie = {
|
|||
hp_max = 20,
|
||||
xp_min = 5,
|
||||
xp_max = 5,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 6.3,
|
||||
head_eye_height = 2.2,
|
||||
curiosity = 7,
|
||||
head_pitch_multiplier=-1,
|
||||
breath_max = -1,
|
||||
armor = {undead = 90, fleshy = 90},
|
||||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 1.8, 0.3},
|
||||
|
@ -62,7 +67,6 @@ local zombie = {
|
|||
{
|
||||
"mobs_mc_empty.png", -- armor
|
||||
"mobs_mc_zombie.png", -- texture
|
||||
"mobs_mc_empty.png", -- wielded_item
|
||||
}
|
||||
},
|
||||
makes_footstep_sound = true,
|
||||
|
@ -129,7 +133,6 @@ husk.textures = {
|
|||
{
|
||||
"mobs_mc_empty.png", -- armor
|
||||
"mobs_mc_husk.png", -- texture
|
||||
"mobs_mc_empty.png", -- wielded_item
|
||||
}
|
||||
}
|
||||
husk.ignited_by_sunlight = false
|
||||
|
@ -144,9 +147,8 @@ mcl_mobs:register_mob("mobs_mc:husk", husk)
|
|||
local baby_husk = table.copy(baby_zombie)
|
||||
baby_husk.description = S("Baby Husk")
|
||||
baby_husk.textures = {{
|
||||
"mobs_mc_empty.png", -- armor
|
||||
"mobs_mc_husk.png", -- texture
|
||||
"mobs_mc_empty.png", -- wielded_item
|
||||
"mobs_mc_husk.png", -- texture
|
||||
}}
|
||||
baby_husk.ignited_by_sunlight = false
|
||||
baby_husk.sunlight_damage = 0
|
||||
|
|
|
@ -25,13 +25,17 @@ local pigman = {
|
|||
group_attack = { "mobs_mc:pigman", "mobs_mc:baby_pigman" },
|
||||
damage = 9,
|
||||
reach = 2,
|
||||
head_swivel = "head.control",
|
||||
bone_eye_height = 2.4,
|
||||
head_eye_height = 1.4,
|
||||
curiosity = 15,
|
||||
collisionbox = {-0.3, -0.01, -0.3, 0.3, 1.94, 0.3},
|
||||
visual = "mesh",
|
||||
mesh = "mobs_mc_zombie_pigman.b3d",
|
||||
textures = { {
|
||||
"mobs_mc_zombie_pigman.png", --pigman
|
||||
"blank.png", --baby
|
||||
"default_tool_goldsword.png", --sword
|
||||
"mobs_mc_zombie_pigman.png", --pigman
|
||||
} },
|
||||
visual_size = {x=3, y=3},
|
||||
sounds = {
|
||||
|
|
|
@ -121,98 +121,8 @@ end
|
|||
local node_stand, node_stand_below, node_head, node_feet, node_head_top
|
||||
local is_swimming
|
||||
|
||||
-- This following part is 2 wrapper functions for player:set_bones
|
||||
-- and player:set_properties preventing them from being resent on
|
||||
-- every globalstep when they have not changed.
|
||||
|
||||
local function roundN(n, d)
|
||||
if type(n) ~= "number" then return n end
|
||||
local m = 10^d
|
||||
return math.floor(n * m + 0.5) / m
|
||||
end
|
||||
|
||||
local function close_enough(a,b)
|
||||
local rt=true
|
||||
if type(a) == "table" and type(b) == "table" then
|
||||
for k,v in pairs(a) do
|
||||
if roundN(v,2) ~= roundN(b[k],2) then
|
||||
rt=false
|
||||
break
|
||||
end
|
||||
end
|
||||
else
|
||||
rt = roundN(a,2) == roundN(b,2)
|
||||
end
|
||||
return rt
|
||||
end
|
||||
|
||||
|
||||
|
||||
local function props_changed(props,oldprops)
|
||||
local changed=false
|
||||
local p={}
|
||||
for k,v in pairs(props) do
|
||||
if not close_enough(v,oldprops[k]) then
|
||||
p[k]=v
|
||||
changed=true
|
||||
end
|
||||
end
|
||||
return changed,p
|
||||
end
|
||||
|
||||
--tests for roundN
|
||||
local test_round1=15
|
||||
local test_round2=15.00199999999
|
||||
local test_round3=15.00111111
|
||||
local test_round4=15.00999999
|
||||
|
||||
assert(roundN(test_round1,2)==roundN(test_round1,2))
|
||||
assert(roundN(test_round1,2)==roundN(test_round2,2))
|
||||
assert(roundN(test_round1,2)==roundN(test_round3,2))
|
||||
assert(roundN(test_round1,2)~=roundN(test_round4,2))
|
||||
|
||||
-- tests for close_enough
|
||||
local test_cb = {-0.35,0,-0.35,0.35,0.8,0.35} --collisionboxes
|
||||
local test_cb_close = {-0.351213,0,-0.35,0.35,0.8,0.351212}
|
||||
local test_cb_diff = {-0.35,0,-1.35,0.35,0.8,0.35}
|
||||
|
||||
local test_eh = 1.65 --eye height
|
||||
local test_eh_close = 1.65123123
|
||||
local test_eh_diff = 1.35
|
||||
|
||||
local test_nt = { r = 225, b = 225, a = 225, g = 225 } --nametag
|
||||
local test_nt_diff = { r = 225, b = 225, a = 0, g = 225 }
|
||||
|
||||
assert(close_enough(test_cb,test_cb_close))
|
||||
assert(not close_enough(test_cb,test_cb_diff))
|
||||
assert(close_enough(test_eh,test_eh_close))
|
||||
assert(not close_enough(test_eh,test_eh_diff))
|
||||
assert(not close_enough(test_nt,test_nt_diff)) --no floats involved here
|
||||
|
||||
--tests for properties_changed
|
||||
local test_properties_set1={collisionbox = {-0.35,0,-0.35,0.35,0.8,0.35}, eye_height = 0.65, nametag_color = { r = 225, b = 225, a = 225, g = 225 }}
|
||||
local test_properties_set2={collisionbox = {-0.35,0,-0.35,0.35,0.8,0.35}, eye_height = 1.35, nametag_color = { r = 225, b = 225, a = 225, g = 225 }}
|
||||
|
||||
local test_p1,_=props_changed(test_properties_set1,test_properties_set1)
|
||||
local test_p2,_=props_changed(test_properties_set1,test_properties_set2)
|
||||
|
||||
assert(not test_p1)
|
||||
assert(test_p2)
|
||||
|
||||
local function set_properties_conditional(player,props)
|
||||
local changed,p=props_changed(props,player:get_properties())
|
||||
if changed then
|
||||
player:set_properties(p)
|
||||
end
|
||||
end
|
||||
|
||||
local function set_bone_position_conditional(player,b,p,r) --bone,position,rotation
|
||||
local oldp,oldr=player:get_bone_position(b)
|
||||
if vector.equals(vector.round(oldp),vector.round(p)) and vector.equals(vector.round(oldr),vector.round(r)) then
|
||||
return
|
||||
end
|
||||
player:set_bone_position(b,p,r)
|
||||
end
|
||||
local set_bone_position_conditional = mcl_util.set_bone_position
|
||||
local set_properties_conditional = mcl_util.set_properties
|
||||
|
||||
local function get_overall_velocity(vector)
|
||||
local v = math.sqrt(vector.x^2 + vector.y^2 + vector.z^2)
|
||||
|
|
Loading…
Reference in a new issue