mirror of
https://github.com/mt-mods/homedecor_modpack.git
synced 2025-07-20 06:10:23 +02:00
Merge remote-tracking branch 'upstream/master'
This commit is contained in:
@ -78,14 +78,63 @@ function lrfurn.fix_sofa_rotation_nsew(pos, placer, itemstack, pointed_thing)
|
||||
minetest.swap_node(pos, { name = node.name, param2 = fdir+colorbits })
|
||||
end
|
||||
|
||||
local physics_cache = {}
|
||||
local seated_cache = {}
|
||||
local offset_cache = {}
|
||||
|
||||
minetest.register_entity("homedecor_seating:seat", {
|
||||
initial_properties = {
|
||||
visual = "cube",
|
||||
--comment out the following when testing so you can see it
|
||||
textures = {"blank.png", "blank.png", "blank.png", "blank.png", "blank.png", "blank.png"},
|
||||
collisionbox = { -0.01, -0.01, -0.01, 0.01, 0.01, 0.01 },
|
||||
selectionbox = { -0.01, -0.01, -0.01, 0.01, 0.01, 0.01, rotate = false },
|
||||
static_save = false,
|
||||
},
|
||||
on_punch = function(self)
|
||||
self.object:remove()
|
||||
end,
|
||||
})
|
||||
|
||||
--we only care about 4 rotations, but just in case someone worldedits, etc - do something other than crash
|
||||
--radians are stupid, using degrees and then converting
|
||||
local p2r = {
|
||||
0*math.pi/180,
|
||||
0*math.pi/180, --correct
|
||||
180*math.pi/180, --correct
|
||||
90*math.pi/180, --correct
|
||||
270*math.pi/180, --correct
|
||||
0*math.pi/180,
|
||||
0*math.pi/180,
|
||||
0*math.pi/180,
|
||||
}
|
||||
p2r[0] = p2r[1]
|
||||
|
||||
local p2r_sofa = {
|
||||
0*math.pi/180,
|
||||
90*math.pi/180, --correct
|
||||
270*math.pi/180, --correct
|
||||
180*math.pi/180, --correct
|
||||
0*math.pi/180, --correct
|
||||
0*math.pi/180,
|
||||
0*math.pi/180,
|
||||
0*math.pi/180,
|
||||
}
|
||||
p2r_sofa[0] = p2r_sofa[1]
|
||||
|
||||
local p2r_facedir = {
|
||||
[0] = 180*math.pi/180,
|
||||
[1] = 90*math.pi/180,
|
||||
[2] = 0*math.pi/180,
|
||||
[3] = 270*math.pi/180,
|
||||
}
|
||||
|
||||
function lrfurn.sit(pos, node, clicker, itemstack, pointed_thing, seats)
|
||||
if not clicker:is_player() then
|
||||
return itemstack
|
||||
end
|
||||
|
||||
if physics_cache[clicker:get_player_name()] then
|
||||
local name = clicker:get_player_name()
|
||||
if seated_cache[name] then --already sitting
|
||||
lrfurn.stand(clicker)
|
||||
return itemstack
|
||||
end
|
||||
@ -113,41 +162,109 @@ function lrfurn.sit(pos, node, clicker, itemstack, pointed_thing, seats)
|
||||
|
||||
--see if we can find a non occupied seat
|
||||
local sit_pos
|
||||
local sit_hash
|
||||
for hash, spos in pairs(valid_seats) do
|
||||
local pstatus = false
|
||||
for _, ref in pairs(minetest.get_objects_inside_radius(spos, 0.5)) do
|
||||
if ref:is_player() then
|
||||
if ref:is_player() and seated_cache[ref:get_player_name()] then
|
||||
pstatus = true
|
||||
end
|
||||
end
|
||||
if not pstatus then sit_pos = spos end
|
||||
if not pstatus then
|
||||
sit_pos = spos
|
||||
sit_hash = hash
|
||||
break;
|
||||
end
|
||||
end
|
||||
if not sit_pos then
|
||||
minetest.chat_send_player(clicker:get_player_name(), "sorry, this seat is currently occupied")
|
||||
minetest.chat_send_player(name, "sorry, this seat is currently occupied")
|
||||
return itemstack
|
||||
end
|
||||
|
||||
--seat the player
|
||||
clicker:set_pos(sit_pos)
|
||||
|
||||
xcompat.player.player_attached[clicker:get_player_name()] = true
|
||||
local entity = minetest.add_entity(sit_pos, "homedecor_seating:seat")
|
||||
if not entity then return itemstack end --catch for when the entity fails to spawn just in case
|
||||
|
||||
clicker:set_attach(entity, "", {x = 0, y = 0, z = 0}, {x = 0, y = 0, z = 0}, true)
|
||||
local nodedef = minetest.registered_nodes[node.name]
|
||||
if nodedef.paramtype2 == "facedir" then
|
||||
entity:set_rotation({x = 0, y = p2r_facedir[node.param2 % 4], z = 0})
|
||||
elseif string.find(node.name, "sofa") then
|
||||
entity:set_rotation({x = 0, y = p2r_sofa[node.param2 % 8], z = 0})
|
||||
else
|
||||
entity:set_rotation({x = 0, y = p2r[node.param2 % 8], z = 0})
|
||||
end
|
||||
|
||||
xcompat.player.player_attached[name] = true
|
||||
xcompat.player.set_animation(clicker, "sit", 0)
|
||||
physics_cache[clicker:get_player_name()] = table.copy(clicker:get_physics_override())
|
||||
clicker:set_physics_override({speed = 0, jump = 0, gravity = 0})
|
||||
seated_cache[name] = minetest.hash_node_position(pos)
|
||||
if seated_cache[name] ~= sit_hash then
|
||||
offset_cache[name] = core.hash_node_position(vector.subtract(pos, sit_pos))
|
||||
end
|
||||
|
||||
return itemstack
|
||||
end
|
||||
|
||||
function lrfurn.stand(clicker)
|
||||
xcompat.player.player_attached[clicker:get_player_name()] = false
|
||||
if physics_cache[clicker:get_player_name()] then
|
||||
clicker:set_physics_override(physics_cache[clicker:get_player_name()])
|
||||
physics_cache[clicker:get_player_name()] = nil
|
||||
else --in case this is called and the cache is empty
|
||||
clicker:set_physics_override({speed = 1, jump = 1, gravity = 1})
|
||||
local name = clicker:get_player_name()
|
||||
xcompat.player.player_attached[name] = false
|
||||
if seated_cache[name] then
|
||||
local attached_to = clicker:get_attach()
|
||||
-- Check, clearobjects might have been called, etc
|
||||
if attached_to then
|
||||
-- Removing also detaches
|
||||
attached_to:remove()
|
||||
end
|
||||
seated_cache[name] = nil
|
||||
offset_cache[name] = nil
|
||||
end
|
||||
end
|
||||
|
||||
-- Called when a seat is destroyed
|
||||
function lrfurn.on_seat_destruct(pos)
|
||||
for name, seatpos in pairs(seated_cache) do
|
||||
if seatpos == minetest.hash_node_position(pos) then
|
||||
local player = minetest.get_player_by_name(name)
|
||||
if player then
|
||||
lrfurn.stand(player)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function lrfurn.on_seat_movenode(from_pos, to_pos)
|
||||
local hashed_from_pos = core.hash_node_position(from_pos)
|
||||
local hashed_to_pos = core.hash_node_position(to_pos)
|
||||
for name, seatpos in pairs(seated_cache) do
|
||||
if seatpos == hashed_from_pos then
|
||||
local player = core.get_player_by_name(name)
|
||||
if player then
|
||||
local attached_to = player:get_attach()
|
||||
-- Check, clearobjects might have been called, etc
|
||||
if attached_to then
|
||||
if offset_cache[name] then
|
||||
-- multi-seat node aka sofas
|
||||
attached_to:set_pos(vector.subtract(to_pos,
|
||||
core.get_position_from_hash(offset_cache[name])))
|
||||
else
|
||||
attached_to:set_pos(to_pos)
|
||||
end
|
||||
seated_cache[name] = hashed_to_pos
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
--if the player gets killed in the seat, handle it
|
||||
minetest.register_on_dieplayer(function(player)
|
||||
if seated_cache[player:get_player_name()] then
|
||||
lrfurn.stand(player)
|
||||
end
|
||||
end)
|
||||
|
||||
dofile(modpath.."/longsofas.lua")
|
||||
dofile(modpath.."/sofas.lua")
|
||||
dofile(modpath.."/armchairs.lua")
|
||||
|
Reference in New Issue
Block a user