mirror of
https://git.minetest.land/VoxeLibre/VoxeLibre.git
synced 2024-08-22 01:47:24 +02:00
Allow players to push minecarts that are not on track
This commit is contained in:
parent
b6e51a3c40
commit
659a387256
@ -136,34 +136,40 @@ local function update_cart_orientation(self,staticdata)
|
|||||||
self.object:set_rotation(rot)
|
self.object:set_rotation(rot)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function direction_away_from_players(self, staticdata)
|
local function vector_away_from_players(self, staticdata)
|
||||||
local objs = minetest.get_objects_inside_radius(self.object:get_pos(), 1.1)
|
local objs = minetest.get_objects_inside_radius(self.object:get_pos(), 1.1)
|
||||||
for n=1,#objs do
|
for n=1,#objs do
|
||||||
local obj = objs[n]
|
local obj = objs[n]
|
||||||
local player_name = obj:get_player_name()
|
local player_name = obj:get_player_name()
|
||||||
if player_name and player_name ~= "" and not ( self._driver and self._driver == player_name ) then
|
if player_name and player_name ~= "" and not ( self._driver and self._driver == player_name ) then
|
||||||
local diff = obj:get_pos() - self.object:get_pos()
|
return obj:get_pos() - self.object:get_pos()
|
||||||
|
|
||||||
local length = vector.distance(vector.new(0,0,0),diff)
|
|
||||||
local vec = diff / length
|
|
||||||
local force = vector.dot( vec, vector.normalize(staticdata.dir) )
|
|
||||||
|
|
||||||
-- Check if this would push past the end of the track and don't move it it would
|
|
||||||
-- This prevents an oscillation that would otherwise occur
|
|
||||||
local dir = staticdata.dir
|
|
||||||
if force > 0 then
|
|
||||||
dir = -dir
|
|
||||||
end
|
|
||||||
if mcl_minecarts:is_rail( staticdata.connected_at + dir ) then
|
|
||||||
if force > 0.5 then
|
|
||||||
return -length * 4
|
|
||||||
elseif force < -0.5 then
|
|
||||||
return length * 4
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
return nil
|
||||||
|
end
|
||||||
|
|
||||||
|
local function direction_away_from_players(self, staticdata)
|
||||||
|
local diff = vector_away_from_players(self, staticdata)
|
||||||
|
if not diff then return 0 end
|
||||||
|
|
||||||
|
local length = vector.distance(vector.new(0,0,0),diff)
|
||||||
|
local vec = diff / length
|
||||||
|
local force = vector.dot( vec, vector.normalize(staticdata.dir) )
|
||||||
|
|
||||||
|
-- Check if this would push past the end of the track and don't move it it would
|
||||||
|
-- This prevents an oscillation that would otherwise occur
|
||||||
|
local dir = staticdata.dir
|
||||||
|
if force > 0 then
|
||||||
|
dir = -dir
|
||||||
|
end
|
||||||
|
if mcl_minecarts:is_rail( staticdata.connected_at + dir ) then
|
||||||
|
if force > 0.5 then
|
||||||
|
return -length * 4
|
||||||
|
elseif force < -0.5 then
|
||||||
|
return length * 4
|
||||||
|
end
|
||||||
|
end
|
||||||
return 0
|
return 0
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -430,6 +436,12 @@ local function do_detached_movement(self, dtime)
|
|||||||
self.object:set_acceleration(accel)
|
self.object:set_acceleration(accel)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local away = vector_away_from_players(self, staticdata)
|
||||||
|
if away then
|
||||||
|
local v = self.object:get_velocity()
|
||||||
|
self.object:set_velocity(v - away)
|
||||||
|
end
|
||||||
|
|
||||||
-- Try to reconnect to rail
|
-- Try to reconnect to rail
|
||||||
local pos_r = vector.round(self.object:get_pos())
|
local pos_r = vector.round(self.object:get_pos())
|
||||||
local node = minetest.get_node(pos_r)
|
local node = minetest.get_node(pos_r)
|
||||||
@ -801,21 +813,25 @@ function mcl_minecarts.place_minecart(itemstack, pointed_thing, placer)
|
|||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
local railpos, node
|
local spawn_pos = pointed_thing.above
|
||||||
|
local cart_dir = vector.new(1,0,0)
|
||||||
|
|
||||||
|
local railtype, railpos, node
|
||||||
if mcl_minecarts:is_rail(pointed_thing.under) then
|
if mcl_minecarts:is_rail(pointed_thing.under) then
|
||||||
railpos = pointed_thing.under
|
railpos = pointed_thing.under
|
||||||
node = minetest.get_node(pointed_thing.under)
|
|
||||||
elseif mcl_minecarts:is_rail(pointed_thing.above) then
|
elseif mcl_minecarts:is_rail(pointed_thing.above) then
|
||||||
railpos = pointed_thing.above
|
railpos = pointed_thing.above
|
||||||
node = minetest.get_node(pointed_thing.above)
|
end
|
||||||
else
|
if railpos then
|
||||||
return
|
spawn_pos = railpos
|
||||||
|
node = minetest.get_node(railpos)
|
||||||
|
railtype = minetest.get_item_group(node.name, "connect_to_raillike")
|
||||||
|
cart_dir = mcl_minecarts:get_rail_direction(railpos, vector.new(1,0,0), nil, nil, railtype)
|
||||||
end
|
end
|
||||||
|
|
||||||
local entity_id = entity_mapping[itemstack:get_name()]
|
local entity_id = entity_mapping[itemstack:get_name()]
|
||||||
local cart = minetest.add_entity(railpos, entity_id)
|
local cart = minetest.add_entity(spawn_pos, entity_id)
|
||||||
local railtype = minetest.get_item_group(node.name, "connect_to_raillike")
|
|
||||||
local cart_dir = mcl_minecarts:get_rail_direction(railpos, vector.new(1,0,0), nil, nil, railtype)
|
|
||||||
cart:set_yaw(minetest.dir_to_yaw(cart_dir))
|
cart:set_yaw(minetest.dir_to_yaw(cart_dir))
|
||||||
|
|
||||||
-- Update static data
|
-- Update static data
|
||||||
@ -829,7 +845,9 @@ function mcl_minecarts.place_minecart(itemstack, pointed_thing, placer)
|
|||||||
le._mcl_minecarts_on_place(le, placer)
|
le._mcl_minecarts_on_place(le, placer)
|
||||||
end
|
end
|
||||||
|
|
||||||
handle_cart_enter(le, railpos)
|
if railpos then
|
||||||
|
handle_cart_enter(le, railpos)
|
||||||
|
end
|
||||||
|
|
||||||
local pname = ""
|
local pname = ""
|
||||||
if placer then
|
if placer then
|
||||||
|
Loading…
Reference in New Issue
Block a user