This is the code for my hot air balloon-set:
Code: Select all
dofile(minetest.get_modpath("hotairballoons") .. "/config.lua")
local function get_sign(i)
if i == 0 then
return 0
else
return i / math.abs(i)
end
end
local designs = {
{ "rainbow_1", "Rainbow Hot Air Balloon Type 1", "rainbow", "hotairballoon.obj" },
{ "rainbow_2", "Rainbow Hot Air Balloon Type 2", "rainbow", "hotairballoon.obj" },
{ "four_colors_1", "Four Colors Hot Air Balloon Type 1", "four_colors", "hotairballoon.obj" },
{ "four_colors_2", "Four Colors Hot Air Balloon Type 2", "four_colors", "hotairballoon.obj" },
{ "stella_1", "Stella Hot Air Balloon Type 1", "stella", "hotairballoon_stella.obj" },
{ "stella_2", "Stella Hot Air Balloon Type 2", "stella", "hotairballoon_stella.obj" }
}
for i = 1, #designs do
local name, description, inv_image, mesh = unpack(designs[i])
local balloon = {
textures = { "hotairballoons:hotair_node_" .. name },
visual = "item",
visual_size = { x = 0.667, y = 0.667 },
backface_culling = false,
physical = true,
collisionbox = { -1, -0.5, -1, 1, 0.5, 1 },
collide_with_objects = true,
driver = nil,
yaw = 0,
vx = 0,
vy = 0,
vz = 0,
}
function balloon:on_rightclick(clicker)
if not clicker or not clicker:is_player() then
return
end
local name = clicker:get_player_name()
if self.driver and clicker == self.driver then
clicker:set_detach()
self.driver = nil
default.player_attached[name] = false
default.player_set_animation(clicker, "stand", 10)
if hotairballoon.one_use == true then
self.object:remove()
end
elseif not self.driver then
self.driver = clicker
clicker:set_attach(self.object, "", { x = -4, y = 10.1, z = 0 }, { x = 0, y = 90, z = 0 })
default.player_attached[name] = true
minetest.after(0.2, function()
default.player_set_animation(clicker, "sit", 10)
end)
self.object:setyaw(clicker:get_look_yaw() - math.pi / 2)
end
end
function balloon:on_activate(staticdata, dtime_s)
self.object:set_armor_groups({ immortal = 1 })
if staticdata then
self.v = tonumber(staticdata)
end
end
function balloon:on_punch(puncher, time_from_last_punch, tool_capabilities, direction)
if not self.driver then self.object:remove() end
if puncher and puncher:is_player() and not self.driver and not minetest.setting_getbool("creative_mode") then
puncher:get_inventory():add_item("main", "hotairballoons:hotair_" .. name)
end
end
function balloon:on_step(dtime)
if self.driver then
self.yaw = self.driver:get_look_yaw()
local yaw = self.object:getyaw()
self.vx = self.object:getvelocity().x
self.vy = self.object:getvelocity().y
self.vz = self.object:getvelocity().z
local ctrl = self.driver:get_player_control()
--Forward/backward
if ctrl.up then
self.vx = self.vx + math.cos(yaw) * 0.4
self.vz = self.vz + math.sin(yaw) * 0.4
end
if ctrl.down then
self.vx = self.vx - math.cos(yaw) * 0.4
self.vz = self.vz - math.sin(yaw) * 0.4
end
--Left/right
if ctrl.left then
self.object:setyaw(self.object:getyaw() + math.pi / 60 + dtime * math.pi / 60)
end
if ctrl.right then
self.object:setyaw(self.object:getyaw() - math.pi / 60 - dtime * math.pi / 60)
end
--up/down
if ctrl.jump then
if self.vy < 1.5 then
self.vy = self.vy + 0.3
end
end
if ctrl.sneak then
if self.vy > -1.5 then
self.vy = self.vy - 0.6
end
end
--
end
if self.vx == 0 and self.vz == 0 and self.vy == 0 then
return
end
--Decelerating
local sx = get_sign(self.vx)
self.vx = self.vx - 0.02 * sx
local sz = get_sign(self.vz)
self.vz = self.vz - 0.02 * sz
local sy = get_sign(self.vy)
self.vy = self.vy - 0.01 * sy
--Stop
if sx ~= get_sign(self.vx) then
self.vx = 0
end
if sz ~= get_sign(self.vz) then
self.vz = 0
end
if sy ~= get_sign(self.vy) then
self.vy = 0
end
--Speed limit
if math.abs(self.vx) > 87 then
self.vx = 87 * get_sign(self.vx)
end
if math.abs(self.vz) > 87 then
self.vz = 87 * get_sign(self.vz)
end
if math.abs(self.vy) > 87 then
self.vz = 87 * get_sign(self.vy)
end
self.object:setvelocity({ x = self.vx, y = self.vy, z = self.vz })
end
minetest.register_entity("hotairballoons:hotair_" .. name, balloon)
minetest.register_craftitem("hotairballoons:hotair_" .. name, {
description = description,
inventory_image = "hotair_" .. inv_image .. "_inv.png",
wield_image = "hotair_" .. inv_image .. "_inv.png",
liquids_pointable = false,
on_place = function(itemstack, placer, pointed_thing)
if pointed_thing.type ~= "node" then
return
end
if minetest.get_node(pointed_thing.above).name ~= "air" then
return
end
pointed_thing.under.y = pointed_thing.under.y + 1
minetest.add_entity(pointed_thing.under, "hotairballoons:hotair_" .. name)
if not minetest.setting_getbool("creative_mode") then
itemstack:take_item()
end
return itemstack
end,
})
minetest.register_node("hotairballoons:hotair_node_" .. name, {
description = description,
tiles = {
{
name = "hotair_" .. name .. ".png",
backface_culling = false,
},
},
paramtype = "light",
drawtype = "mesh",
mesh = mesh,
groups = { not_in_creative_inventory = 1 },
})
end
Someone created a simple hot air balloon from a flying carpet mod, created by a third person.
i modifyed the model for better proportions (balloon bigger, in relation to the basket) and added a seccond, more specific model for a balloon, that looks like Stella, the pink bird from the "Angry Birds".
Stella is my favorite character from theese birds, and in the classic version (not the movie) she is round, just like most members of the flock.
So i thaught, she can be a good design for a hot air balloon.
for all designs i created a texture with the realistic looking open bottom area of the balloon-hull.
And i use a node with a .obj-mesh as visualisation, because it has a better shading then directly using a .b3d-mesh.
I use this variant .for all vehicle-entities (living entities are another thing, because they need an animation-skeleton).