6 local function is_water(pos)
7 local nn = minetest.get_node(pos).name
8 return minetest.get_item_group(nn, "water") ~= 0
11 local function get_sign(i)
19 local function get_velocity(v, yaw, y)
20 local x = -math.sin(yaw)*v
21 local z = math.cos(yaw)*v
22 return {x=x, y=y, z=z}
25 local function get_v(v)
26 return math.sqrt(v.x^2+v.z^2)
35 collisionbox = {-0.6,-0.4,-0.6, 0.6,0.3,0.6},
38 textures = {"default_wood.png"},
46 function boat.on_rightclick(self, clicker)
47 if not clicker or not clicker:is_player() then
50 local name = clicker:get_player_name()
51 if self.driver and clicker == self.driver then
54 default.player_attached[name] = false
55 default.player_set_animation(clicker, "stand" , 30)
56 elseif not self.driver then
58 clicker:set_attach(self.object, "", {x=0,y=11,z=-3}, {x=0,y=0,z=0})
59 default.player_attached[name] = true
60 minetest.after(0.2, function()
61 default.player_set_animation(clicker, "sit" , 30)
63 self.object:setyaw(clicker:get_look_yaw()-math.pi/2)
67 function boat.on_activate(self, staticdata, dtime_s)
68 self.object:set_armor_groups({immortal=1})
70 self.v = tonumber(staticdata)
75 function boat.get_staticdata()
79 function boat.on_punch(self, puncher, time_from_last_punch, tool_capabilities, direction)
80 if not puncher or not puncher:is_player() or self.removed then
84 default.player_attached[puncher:get_player_name()] = false
87 -- delay remove to ensure player is detached
88 minetest.after(0.1,function()
91 if not minetest.setting_getbool("creative_mode") then
92 puncher:get_inventory():add_item("main", "boats:boat")
96 function boat.on_step(self, dtime)
97 self.v = get_v(self.object:getvelocity())*get_sign(self.v)
99 local ctrl = self.driver:get_player_control()
100 local yaw = self.object:getyaw()
109 self.object:setyaw(yaw-math.pi/120-dtime*math.pi/120)
111 self.object:setyaw(yaw+math.pi/120+dtime*math.pi/120)
116 self.object:setyaw(yaw+math.pi/120+dtime*math.pi/120)
118 self.object:setyaw(yaw-math.pi/120-dtime*math.pi/120)
122 local velo = self.object:getvelocity()
123 if self.v == 0 and velo.x == 0 and velo.z == 0 then
126 local s = get_sign(self.v)
127 self.v = self.v - 0.02*s
128 if s ~= get_sign(self.v) then
129 self.object:setvelocity({x=0, y=0, z=0})
133 if math.abs(self.v) > 4.5 then
134 self.v = 4.5*get_sign(self.v)
137 local p = self.object:getpos()
139 local new_velo = {x=0,y=0,z=0}
140 local new_acce = {x=0,y=0,z=0}
141 if not is_water(p) then
142 if minetest.registered_nodes[minetest.env:get_node(p).name].walkable then
145 new_acce = {x=0, y=-10, z=0}
146 new_velo = get_velocity(self.v, self.object:getyaw(), self.object:getvelocity().y)
150 new_acce = {x=0, y=3, z=0}
151 local y = self.object:getvelocity().y
156 self.object:setacceleration({x=0, y=10, z=0})
158 new_velo = get_velocity(self.v, self.object:getyaw(), y)
160 new_acce = {x=0, y=0, z=0}
161 if math.abs(self.object:getvelocity().y) < 1 then
162 local pos = self.object:getpos()
163 pos.y = math.floor(pos.y)+0.5
164 self.object:setpos(pos)
165 new_velo = get_velocity(self.v, self.object:getyaw(), 0)
167 new_velo = get_velocity(self.v, self.object:getyaw(), self.object:getvelocity().y)
171 self.object:setvelocity(new_velo)
172 self.object:setacceleration(new_acce)
175 minetest.register_entity("boats:boat", boat)
178 minetest.register_craftitem("boats:boat", {
179 description = "Boat",
180 inventory_image = "boat_inventory.png",
181 wield_image = "boat_wield.png",
182 wield_scale = {x=2, y=2, z=1},
183 liquids_pointable = true,
185 on_place = function(itemstack, placer, pointed_thing)
186 if pointed_thing.type ~= "node" then
189 if not is_water(pointed_thing.under) then
192 pointed_thing.under.y = pointed_thing.under.y+0.5
193 minetest.add_entity(pointed_thing.under, "boats:boat")
194 if not minetest.setting_getbool("creative_mode") then
195 itemstack:take_item()
201 minetest.register_craft({
202 output = "boats:boat",
205 {"group:wood", "", "group:wood"},
206 {"group:wood", "group:wood", "group:wood"},