Convert to ModPack
52
README.md
@ -1,28 +1,34 @@
|
||||
Capture The Flag
|
||||
================
|
||||
CTF PvP Engine
|
||||
==============
|
||||
|
||||
This is a highly customisable game for PvP servers.
|
||||
A highly modular framework for the Minetest game engine, in order to allow
|
||||
the development of Capture the Flag / City vs City games. Good for any
|
||||
sort of game where players can join teams - flags are optional, everything
|
||||
is highly configurable.
|
||||
|
||||
All settings and features can be modified by editing the settings in this game's configuration.
|
||||
Licenses
|
||||
========
|
||||
|
||||
**See forum thread for instructions and feature**
|
||||
Created by: [rubenwardy](http://rubenwardy.com/).
|
||||
Copyright (c) 2013 - 2015
|
||||
**Code:** LGPL 2.1 or later.
|
||||
**Textures:** CC-BY-SA 3.0
|
||||
|
||||
What is this game for?
|
||||
----------------------
|
||||
Modules
|
||||
=======
|
||||
|
||||
This game can be used for many PvP purposes.
|
||||
|
||||
* Traditional capture the flag.
|
||||
* Country wars - players can make cities and defend them.
|
||||
* Obstacle courses - players can make their bases hard to get to with traps.
|
||||
|
||||
License
|
||||
-------
|
||||
|
||||
This mod was made by Andrew "rubenwardy" Ward.
|
||||
|
||||
License for Code: LGPL 2.1 or later.
|
||||
License for Textures: CC BY-SA 3.0 or later.
|
||||
|
||||
This subgame is a fork of minetest_game with capture the flag mods added.
|
||||
minetest_game is licensed under LGPL 2.1 or later for code, and CC BY-SA 3.0 or later for textures.
|
||||
* ctf
|
||||
* core - adds saving, loading and settings. All modules depend on this.
|
||||
* teams - add the concepts of teams and players. All modules except core depend on this.
|
||||
* diplomacy - adds inter team states of war, peace and alliances.
|
||||
Requires ctf.teams
|
||||
* gui - adds the team gui on /team. Allows tabs to be registered.
|
||||
* hud - adds the name of the team in the TR of the screen, and sets the color
|
||||
of a player's name.
|
||||
* ctf_chat - adds chat commands and chat channels.
|
||||
* ctf_flag - adds flags and flag taking.
|
||||
* ctf_match - adds the concept of winning, match build time,
|
||||
and reseting the map / setting up a new game.
|
||||
Requires ctf_flag
|
||||
* ctf_protect - Adds node ownership / protection to teams. Requires ctf_flag.
|
||||
* ctf_turret - Adds auto-firing turrets that fire on enemies.
|
||||
|
Before Width: | Height: | Size: 6.5 KiB After Width: | Height: | Size: 6.5 KiB |
Before Width: | Height: | Size: 9.0 KiB After Width: | Height: | Size: 9.0 KiB |
Before Width: | Height: | Size: 8.8 KiB After Width: | Height: | Size: 8.8 KiB |
Before Width: | Height: | Size: 601 B After Width: | Height: | Size: 601 B |
Before Width: | Height: | Size: 598 B After Width: | Height: | Size: 598 B |
Before Width: | Height: | Size: 776 B After Width: | Height: | Size: 776 B |
Before Width: | Height: | Size: 732 B After Width: | Height: | Size: 732 B |
Before Width: | Height: | Size: 666 B After Width: | Height: | Size: 666 B |
Before Width: | Height: | Size: 676 B After Width: | Height: | Size: 676 B |
Before Width: | Height: | Size: 618 B After Width: | Height: | Size: 618 B |
Before Width: | Height: | Size: 625 B After Width: | Height: | Size: 625 B |
Before Width: | Height: | Size: 549 B After Width: | Height: | Size: 549 B |
Before Width: | Height: | Size: 571 B After Width: | Height: | Size: 571 B |
Before Width: | Height: | Size: 826 B After Width: | Height: | Size: 826 B |
Before Width: | Height: | Size: 775 B After Width: | Height: | Size: 775 B |
Before Width: | Height: | Size: 632 B After Width: | Height: | Size: 632 B |
Before Width: | Height: | Size: 635 B After Width: | Height: | Size: 635 B |
Before Width: | Height: | Size: 690 B After Width: | Height: | Size: 690 B |
Before Width: | Height: | Size: 688 B After Width: | Height: | Size: 688 B |
Before Width: | Height: | Size: 622 B After Width: | Height: | Size: 622 B |
Before Width: | Height: | Size: 616 B After Width: | Height: | Size: 616 B |
Before Width: | Height: | Size: 812 B After Width: | Height: | Size: 812 B |
Before Width: | Height: | Size: 874 B After Width: | Height: | Size: 874 B |
Before Width: | Height: | Size: 544 B After Width: | Height: | Size: 544 B |
Before Width: | Height: | Size: 567 B After Width: | Height: | Size: 567 B |
Before Width: | Height: | Size: 657 B After Width: | Height: | Size: 657 B |
Before Width: | Height: | Size: 671 B After Width: | Height: | Size: 671 B |
Before Width: | Height: | Size: 251 B After Width: | Height: | Size: 251 B |
BIN
menu/header.png
Before Width: | Height: | Size: 152 KiB |
BIN
menu/icon.png
Before Width: | Height: | Size: 3.5 KiB |
@ -1,67 +0,0 @@
|
||||
# These settings are out of date,
|
||||
# look for `ctf._set(` lines in mods/capturetheflag/ etc and prepend `ctf.`
|
||||
|
||||
# Whether teams own the nodes around their flag
|
||||
#ctf.node_ownership = true
|
||||
#ctf.flag_protect_distance = 25
|
||||
|
||||
# Can teams have multiple flags?
|
||||
#ctf.multiple_flags = true
|
||||
|
||||
# Whether flags need to be taken to other teams flag to win
|
||||
#ctf.flag_capture_take = false
|
||||
|
||||
# Are GUIs enabled
|
||||
#ctf.gui = true
|
||||
|
||||
# Is the HUD enabled
|
||||
#ctf.hud = true
|
||||
|
||||
# Team GUI on /team
|
||||
#ctf.team_gui = true
|
||||
|
||||
# Default tab when opening Team GUI
|
||||
# news
|
||||
# flags
|
||||
# diplo
|
||||
# settings
|
||||
#ctf.gui.team.initial = news
|
||||
|
||||
# Enable tabs in Team GUI
|
||||
#ctf.flag_teleport_gui = true
|
||||
#ctf.news_gui = true
|
||||
#ctf.diplomacy = true
|
||||
|
||||
# Show the spawn as a target in flag teleport Team GUI
|
||||
#ctf.spawn_in_flag_teleport_gui = false
|
||||
|
||||
# Can flags have names?
|
||||
#ctf.flag_names = true
|
||||
|
||||
# Do teams have their own chat channel?
|
||||
#ctf.team_channel = true
|
||||
|
||||
# Can players chat with other teams on /all. If team_channel is disabled, this setting does nothing.
|
||||
#ctf.global_channel = true
|
||||
|
||||
# Can players change teams using /join?
|
||||
#ctf.players_can_change_team",true)
|
||||
|
||||
# How are players allocated to teams?
|
||||
# 0: none,
|
||||
# 1: random,
|
||||
# 2: one of first two largest groups,
|
||||
# 3 smallest group
|
||||
#ctf.allocate_mode = 0
|
||||
|
||||
# Maximum number in team, obeyed by allocation and /join. Admins don't obey this
|
||||
#ctf.maximum_in_team = -1
|
||||
|
||||
# The default Diplomacy state (if diplomacy is enabled)
|
||||
# war
|
||||
# peace
|
||||
# alliance
|
||||
#ctf.default_diplo_state = war
|
||||
|
||||
# Chatplus distance - how far players can hear each other
|
||||
#ctf.chatplus_distance = -1
|
@ -1,18 +0,0 @@
|
||||
1.0.1 beta
|
||||
----------
|
||||
- Add backwards compatibility with PilzAdam's beds mod
|
||||
- Fix placement
|
||||
- Fix small bugs
|
||||
- Prevent possible crash
|
||||
|
||||
1.1
|
||||
---
|
||||
- Add fancy bed model (based on jp's model)
|
||||
- Add API to register beds
|
||||
- Allow players always to detach from bed (by donat-b)
|
||||
- If more than 50% of players want sleep they can skip the night
|
||||
- Don't show sleep dialog in singleplayer
|
||||
|
||||
1.1.1
|
||||
-----
|
||||
- Prevent possbile crash by trying to reposition leaving players
|
@ -1,29 +0,0 @@
|
||||
Minetest mod "Beds"
|
||||
===================
|
||||
by BlockMen (c) 2014-2015
|
||||
|
||||
Version: 1.1.1
|
||||
|
||||
About
|
||||
~~~~~
|
||||
This mod adds a bed to Minetest which allows to skip the night. To sleep rightclick the bed, if playing
|
||||
in singleplayer mode the night gets skipped imideatly. If playing on server you get shown how many other
|
||||
players are in bed too. If all players are sleeping the night gets skipped aswell. Also the night skip can be forced
|
||||
if more than 50% of the players are lying in bed and use this option.
|
||||
|
||||
Another feature is a controled respawning. If you have slept in bed (not just lying in it) your respawn point
|
||||
is set to the beds location and you will respawn there after death.
|
||||
You can disable the respawn at beds by setting "enable_bed_respawn = false" in minetest.conf
|
||||
|
||||
|
||||
|
||||
License of source code, textures: WTFPL
|
||||
---------------------------------------
|
||||
(c) Copyright BlockMen (2014-2015)
|
||||
|
||||
|
||||
This program is free software. It comes without any warranty, to
|
||||
the extent permitted by applicable law. You can redistribute it
|
||||
and/or modify it under the terms of the Do What The Fuck You Want
|
||||
To Public License, Version 2, as published by Sam Hocevar. See
|
||||
http://sam.zoy.org/wtfpl/COPYING for more details.
|
@ -1,111 +0,0 @@
|
||||
function beds.register_bed(name, def)
|
||||
minetest.register_node(name .. "_bottom", {
|
||||
description = def.description,
|
||||
inventory_image = def.inventory_image,
|
||||
wield_image = def.wield_image,
|
||||
drawtype = "nodebox",
|
||||
tiles = def.tiles.bottom,
|
||||
paramtype = "light",
|
||||
paramtype2 = "facedir",
|
||||
is_ground_content = false,
|
||||
stack_max = 1,
|
||||
groups = {snappy = 1, choppy = 2, oddly_breakable_by_hand = 2, flammable = 3, bed = 1},
|
||||
sounds = default.node_sound_wood_defaults(),
|
||||
node_box = {
|
||||
type = "fixed",
|
||||
fixed = def.nodebox.bottom,
|
||||
},
|
||||
selection_box = {
|
||||
type = "fixed",
|
||||
fixed = def.selectionbox,
|
||||
|
||||
},
|
||||
after_place_node = function(pos, placer, itemstack)
|
||||
local n = minetest.get_node_or_nil(pos)
|
||||
if not n or not n.param2 then
|
||||
minetest.remove_node(pos)
|
||||
return true
|
||||
end
|
||||
local dir = minetest.facedir_to_dir(n.param2)
|
||||
local p = vector.add(pos, dir)
|
||||
local n2 = minetest.get_node_or_nil(p)
|
||||
local def = n2 and minetest.registered_items[n2.name]
|
||||
if not def or not def.buildable_to then
|
||||
minetest.remove_node(pos)
|
||||
return true
|
||||
end
|
||||
minetest.set_node(p, {name = n.name:gsub("%_bottom", "_top"), param2 = n.param2})
|
||||
return false
|
||||
end,
|
||||
on_destruct = function(pos)
|
||||
local n = minetest.get_node_or_nil(pos)
|
||||
if not n then return end
|
||||
local dir = minetest.facedir_to_dir(n.param2)
|
||||
local p = vector.add(pos, dir)
|
||||
local n2 = minetest.get_node(p)
|
||||
if minetest.get_item_group(n2.name, "bed") == 2 and n.param2 == n2.param2 then
|
||||
minetest.remove_node(p)
|
||||
end
|
||||
end,
|
||||
on_rightclick = function(pos, node, clicker)
|
||||
beds.on_rightclick(pos, clicker)
|
||||
end,
|
||||
on_rotate = function(pos, node, user, mode, new_param2)
|
||||
local dir = minetest.facedir_to_dir(node.param2)
|
||||
local p = vector.add(pos, dir)
|
||||
local node2 = minetest.get_node_or_nil(p)
|
||||
if not node2 or not minetest.get_item_group(node2.name, "bed") == 2 or
|
||||
not node.param2 == node2.param2 then
|
||||
return false
|
||||
end
|
||||
if minetest.is_protected(p, user:get_player_name()) then
|
||||
minetest.record_protection_violation(p, user:get_player_name())
|
||||
return false
|
||||
end
|
||||
if mode ~= screwdriver.ROTATE_FACE then
|
||||
return false
|
||||
end
|
||||
local newp = vector.add(pos, minetest.facedir_to_dir(new_param2))
|
||||
local node3 = minetest.get_node_or_nil(newp)
|
||||
local def = node3 and minetest.registered_nodes[node3.name]
|
||||
if not def or not def.buildable_to then
|
||||
return false
|
||||
end
|
||||
if minetest.is_protected(newp, user:get_player_name()) then
|
||||
minetest.record_protection_violation(newp, user:get_player_name())
|
||||
return false
|
||||
end
|
||||
node.param2 = new_param2
|
||||
minetest.swap_node(pos, node)
|
||||
minetest.remove_node(p)
|
||||
minetest.set_node(newp, {name = node.name:gsub("%_bottom", "_top"), param2 = new_param2})
|
||||
return true
|
||||
end,
|
||||
})
|
||||
|
||||
minetest.register_node(name .. "_top", {
|
||||
drawtype = "nodebox",
|
||||
tiles = def.tiles.top,
|
||||
paramtype = "light",
|
||||
paramtype2 = "facedir",
|
||||
is_ground_content = false,
|
||||
groups = {snappy = 1, choppy = 2, oddly_breakable_by_hand = 2, flammable = 3, bed = 2},
|
||||
sounds = default.node_sound_wood_defaults(),
|
||||
node_box = {
|
||||
type = "fixed",
|
||||
fixed = def.nodebox.top,
|
||||
},
|
||||
selection_box = {
|
||||
type = "fixed",
|
||||
fixed = {0, 0, 0, 0, 0, 0},
|
||||
},
|
||||
})
|
||||
|
||||
minetest.register_alias(name, name .. "_bottom")
|
||||
|
||||
-- register recipe
|
||||
minetest.register_craft({
|
||||
output = name,
|
||||
recipe = def.recipe
|
||||
})
|
||||
end
|
@ -1,88 +0,0 @@
|
||||
-- fancy shaped bed
|
||||
beds.register_bed("beds:fancy_bed", {
|
||||
description = "Fancy Bed",
|
||||
inventory_image = "beds_bed_fancy.png",
|
||||
wield_image = "beds_bed_fancy.png",
|
||||
tiles = {
|
||||
bottom = {
|
||||
"beds_bed_top1.png",
|
||||
"default_wood.png",
|
||||
"beds_bed_side1.png",
|
||||
"beds_bed_side1.png^[transformFX",
|
||||
"default_wood.png",
|
||||
"beds_bed_foot.png",
|
||||
},
|
||||
top = {
|
||||
"beds_bed_top2.png",
|
||||
"default_wood.png",
|
||||
"beds_bed_side2.png",
|
||||
"beds_bed_side2.png^[transformFX",
|
||||
"beds_bed_head.png",
|
||||
"default_wood.png",
|
||||
}
|
||||
},
|
||||
nodebox = {
|
||||
bottom = {
|
||||
{-0.5, -0.5, -0.5, -0.375, -0.065, -0.4375},
|
||||
{0.375, -0.5, -0.5, 0.5, -0.065, -0.4375},
|
||||
{-0.5, -0.375, -0.5, 0.5, -0.125, -0.4375},
|
||||
{-0.5, -0.375, -0.5, -0.4375, -0.125, 0.5},
|
||||
{0.4375, -0.375, -0.5, 0.5, -0.125, 0.5},
|
||||
{-0.4375, -0.3125, -0.4375, 0.4375, -0.0625, 0.5},
|
||||
},
|
||||
top = {
|
||||
{-0.5, -0.5, 0.4375, -0.375, 0.1875, 0.5},
|
||||
{0.375, -0.5, 0.4375, 0.5, 0.1875, 0.5},
|
||||
{-0.5, 0, 0.4375, 0.5, 0.125, 0.5},
|
||||
{-0.5, -0.375, 0.4375, 0.5, -0.125, 0.5},
|
||||
{-0.5, -0.375, -0.5, -0.4375, -0.125, 0.5},
|
||||
{0.4375, -0.375, -0.5, 0.5, -0.125, 0.5},
|
||||
{-0.4375, -0.3125, -0.5, 0.4375, -0.0625, 0.4375},
|
||||
}
|
||||
},
|
||||
selectionbox = {-0.5, -0.5, -0.5, 0.5, 0.06, 1.5},
|
||||
recipe = {
|
||||
{"", "", "group:stick"},
|
||||
{"wool:red", "wool:red", "wool:white"},
|
||||
{"group:wood", "group:wood", "group:wood"},
|
||||
},
|
||||
})
|
||||
|
||||
-- simple shaped bed
|
||||
beds.register_bed("beds:bed", {
|
||||
description = "Simple Bed",
|
||||
inventory_image = "beds_bed.png",
|
||||
wield_image = "beds_bed.png",
|
||||
tiles = {
|
||||
bottom = {
|
||||
"beds_bed_top_bottom.png^[transformR90",
|
||||
"default_wood.png",
|
||||
"beds_bed_side_bottom_r.png",
|
||||
"beds_bed_side_bottom_r.png^[transformfx",
|
||||
"beds_transparent.png",
|
||||
"beds_bed_side_bottom.png"
|
||||
},
|
||||
top = {
|
||||
"beds_bed_top_top.png^[transformR90",
|
||||
"default_wood.png",
|
||||
"beds_bed_side_top_r.png",
|
||||
"beds_bed_side_top_r.png^[transformfx",
|
||||
"beds_bed_side_top.png",
|
||||
"beds_transparent.png",
|
||||
}
|
||||
},
|
||||
nodebox = {
|
||||
bottom = {-0.5, -0.5, -0.5, 0.5, 0.06, 0.5},
|
||||
top = {-0.5, -0.5, -0.5, 0.5, 0.06, 0.5},
|
||||
},
|
||||
selectionbox = {-0.5, -0.5, -0.5, 0.5, 0.06, 1.5},
|
||||
recipe = {
|
||||
{"wool:red", "wool:red", "wool:white"},
|
||||
{"group:wood", "group:wood", "group:wood"}
|
||||
},
|
||||
|
||||
})
|
||||
|
||||
-- aliases for PA's beds mod
|
||||
minetest.register_alias("beds:bed_bottom_red", "beds:bed_bottom")
|
||||
minetest.register_alias("beds:bed_top_red", "beds:bed_top")
|
@ -1,2 +0,0 @@
|
||||
default
|
||||
wool
|
@ -1,213 +0,0 @@
|
||||
local player_in_bed = 0
|
||||
local is_sp = minetest.is_singleplayer()
|
||||
local enable_respawn = minetest.setting_getbool("enable_bed_respawn")
|
||||
if enable_respawn == nil then
|
||||
enable_respawn = true
|
||||
end
|
||||
|
||||
|
||||
-- helper functions
|
||||
|
||||
local function get_look_yaw(pos)
|
||||
local n = minetest.get_node(pos)
|
||||
if n.param2 == 1 then
|
||||
return 7.9, n.param2
|
||||
elseif n.param2 == 3 then
|
||||
return 4.75, n.param2
|
||||
elseif n.param2 == 0 then
|
||||
return 3.15, n.param2
|
||||
else
|
||||
return 6.28, n.param2
|
||||
end
|
||||
end
|
||||
|
||||
local function check_in_beds(players)
|
||||
local in_bed = beds.player
|
||||
if not players then
|
||||
players = minetest.get_connected_players()
|
||||
end
|
||||
|
||||
for n, player in ipairs(players) do
|
||||
local name = player:get_player_name()
|
||||
if not in_bed[name] then
|
||||
return false
|
||||
end
|
||||
end
|
||||
|
||||
return #players > 0
|
||||
end
|
||||
|
||||
local function lay_down(player, pos, bed_pos, state, skip)
|
||||
local name = player:get_player_name()
|
||||
local hud_flags = player:hud_get_flags()
|
||||
|
||||
if not player or not name then
|
||||
return
|
||||
end
|
||||
|
||||
-- stand up
|
||||
if state ~= nil and not state then
|
||||
local p = beds.pos[name] or nil
|
||||
if beds.player[name] ~= nil then
|
||||
beds.player[name] = nil
|
||||
player_in_bed = player_in_bed - 1
|
||||
end
|
||||
-- skip here to prevent sending player specific changes (used for leaving players)
|
||||
if skip then
|
||||
return
|
||||
end
|
||||
if p then
|
||||
player:setpos(p)
|
||||
end
|
||||
|
||||
-- physics, eye_offset, etc
|
||||
player:set_eye_offset({x=0,y=0,z=0}, {x=0,y=0,z=0})
|
||||
player:set_look_yaw(math.random(1, 180)/100)
|
||||
default.player_attached[name] = false
|
||||
player:set_physics_override(1, 1, 1)
|
||||
hud_flags.wielditem = true
|
||||
default.player_set_animation(player, "stand" , 30)
|
||||
|
||||
-- lay down
|
||||
else
|
||||
beds.player[name] = 1
|
||||
beds.pos[name] = pos
|
||||
player_in_bed = player_in_bed + 1
|
||||
|
||||
-- physics, eye_offset, etc
|
||||
player:set_eye_offset({x=0,y=-13,z=0}, {x=0,y=0,z=0})
|
||||
local yaw, param2 = get_look_yaw(bed_pos)
|
||||
player:set_look_yaw(yaw)
|
||||
local dir = minetest.facedir_to_dir(param2)
|
||||
local p = {x=bed_pos.x+dir.x/2,y=bed_pos.y,z=bed_pos.z+dir.z/2}
|
||||
player:set_physics_override(0, 0, 0)
|
||||
player:setpos(p)
|
||||
default.player_attached[name] = true
|
||||
hud_flags.wielditem = false
|
||||
default.player_set_animation(player, "lay" , 0)
|
||||
end
|
||||
|
||||
player:hud_set_flags(hud_flags)
|
||||
end
|
||||
|
||||
local function update_formspecs(finished)
|
||||
local ges = #minetest.get_connected_players()
|
||||
local form_n = ""
|
||||
local is_majority = (ges/2) < player_in_bed
|
||||
|
||||
if finished then
|
||||
form_n = beds.formspec ..
|
||||
"label[2.7,11; Good morning.]"
|
||||
else
|
||||
form_n = beds.formspec ..
|
||||
"label[2.2,11;"..tostring(player_in_bed).." of "..tostring(ges).." players are in bed]"
|
||||
if is_majority then
|
||||
form_n = form_n ..
|
||||
"button_exit[2,8;4,0.75;force;Force night skip]"
|
||||
end
|
||||
end
|
||||
|
||||
for name,_ in pairs(beds.player) do
|
||||
minetest.show_formspec(name, "beds_form", form_n)
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
-- public functions
|
||||
|
||||
function beds.kick_players()
|
||||
for name,_ in pairs(beds.player) do
|
||||
local player = minetest.get_player_by_name(name)
|
||||
lay_down(player, nil, nil, false)
|
||||
end
|
||||
end
|
||||
|
||||
function beds.skip_night()
|
||||
minetest.set_timeofday(0.23)
|
||||
beds.set_spawns()
|
||||
end
|
||||
|
||||
function beds.on_rightclick(pos, player)
|
||||
local name = player:get_player_name()
|
||||
local ppos = player:getpos()
|
||||
local tod = minetest.get_timeofday()
|
||||
|
||||
if tod > 0.2 and tod < 0.805 then
|
||||
if beds.player[name] then
|
||||
lay_down(player, nil, nil, false)
|
||||
end
|
||||
minetest.chat_send_player(name, "You can only sleep at night.")
|
||||
return
|
||||
end
|
||||
|
||||
-- move to bed
|
||||
if not beds.player[name] then
|
||||
lay_down(player, ppos, pos)
|
||||
else
|
||||
lay_down(player, nil, nil, false)
|
||||
end
|
||||
|
||||
if not is_sp then
|
||||
update_formspecs(false)
|
||||
end
|
||||
|
||||
-- skip the night and let all players stand up
|
||||
if check_in_beds() then
|
||||
minetest.after(2, function()
|
||||
beds.skip_night()
|
||||
if not is_sp then
|
||||
update_formspecs(true)
|
||||
end
|
||||
beds.kick_players()
|
||||
end)
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
-- callbacks
|
||||
|
||||
minetest.register_on_joinplayer(function(player)
|
||||
beds.read_spawns()
|
||||
end)
|
||||
|
||||
-- respawn player at bed if enabled and valid position is found
|
||||
minetest.register_on_respawnplayer(function(player)
|
||||
if not enable_respawn then
|
||||
return false
|
||||
end
|
||||
local name = player:get_player_name()
|
||||
local pos = beds.spawn[name] or nil
|
||||
if pos then
|
||||
player:setpos(pos)
|
||||
return true
|
||||
end
|
||||
end)
|
||||
|
||||
minetest.register_on_leaveplayer(function(player)
|
||||
local name = player:get_player_name()
|
||||
lay_down(player, nil, nil, false, true)
|
||||
beds.player[name] = nil
|
||||
if check_in_beds() then
|
||||
minetest.after(2, function()
|
||||
beds.skip_night()
|
||||
update_formspecs(true)
|
||||
beds.kick_players()
|
||||
end)
|
||||
end
|
||||
end)
|
||||
|
||||
minetest.register_on_player_receive_fields(function(player, formname, fields)
|
||||
if formname ~= "beds_form" then
|
||||
return
|
||||
end
|
||||
if fields.quit or fields.leave then
|
||||
lay_down(player, nil, nil, false)
|
||||
update_formspecs(false)
|
||||
end
|
||||
|
||||
if fields.force then
|
||||
beds.skip_night()
|
||||
update_formspecs(true)
|
||||
beds.kick_players()
|
||||
end
|
||||
end)
|
@ -1,16 +0,0 @@
|
||||
beds = {}
|
||||
beds.player = {}
|
||||
beds.pos = {}
|
||||
beds.spawn = {}
|
||||
|
||||
beds.formspec = "size[8,15;true]"..
|
||||
"bgcolor[#080808BB; true]"..
|
||||
"button_exit[2,12;4,0.75;leave;Leave Bed]"
|
||||
|
||||
local modpath = minetest.get_modpath("beds")
|
||||
|
||||
-- load files
|
||||
dofile(modpath.."/functions.lua")
|
||||
dofile(modpath.."/api.lua")
|
||||
dofile(modpath.."/beds.lua")
|
||||
dofile(modpath.."/spawns.lua")
|
@ -1,58 +0,0 @@
|
||||
local world_path = minetest.get_worldpath()
|
||||
local org_file = world_path .. "/beds_spawns"
|
||||
local file = world_path .. "/beds_spawns"
|
||||
local bkwd = false
|
||||
|
||||
-- check for PA's beds mod spawns
|
||||
local cf = io.open(world_path .. "/beds_player_spawns", "r")
|
||||
if cf ~= nil then
|
||||
io.close(cf)
|
||||
file = world_path .. "/beds_player_spawns"
|
||||
bkwd = true
|
||||
end
|
||||
|
||||
function beds.read_spawns()
|
||||
local spawns = beds.spawn
|
||||
local input = io.open(file, "r")
|
||||
if input and not bkwd then
|
||||
repeat
|
||||
local x = input:read("*n")
|
||||
if x == nil then
|
||||
break
|
||||
end
|
||||
local y = input:read("*n")
|
||||
local z = input:read("*n")
|
||||
local name = input:read("*l")
|
||||
spawns[name:sub(2)] = {x = x, y = y, z = z}
|
||||
until input:read(0) == nil
|
||||
io.close(input)
|
||||
elseif input and bkwd then
|
||||
beds.spawn = minetest.deserialize(input:read("*all"))
|
||||
input:close()
|
||||
beds.save_spawns()
|
||||
os.rename(file, file .. ".backup")
|
||||
file = org_file
|
||||
else
|
||||
spawns = {}
|
||||
end
|
||||
end
|
||||
|
||||
function beds.save_spawns()
|
||||
if not beds.spawn then
|
||||
return
|
||||
end
|
||||
local output = io.open(org_file, "w")
|
||||
for i, v in pairs(beds.spawn) do
|
||||
output:write(v.x.." "..v.y.." "..v.z.." "..i.."\n")
|
||||
end
|
||||
io.close(output)
|
||||
end
|
||||
|
||||
function beds.set_spawns()
|
||||
for name,_ in pairs(beds.player) do
|
||||
local player = minetest.get_player_by_name(name)
|
||||
local p = player:getpos()
|
||||
beds.spawn[name] = p
|
||||
end
|
||||
beds.save_spawns()
|
||||
end
|
Before Width: | Height: | Size: 540 B |
Before Width: | Height: | Size: 537 B |
Before Width: | Height: | Size: 390 B |
Before Width: | Height: | Size: 387 B |
Before Width: | Height: | Size: 296 B |
Before Width: | Height: | Size: 316 B |
Before Width: | Height: | Size: 561 B |
Before Width: | Height: | Size: 537 B |
Before Width: | Height: | Size: 611 B |
Before Width: | Height: | Size: 596 B |
Before Width: | Height: | Size: 583 B |
Before Width: | Height: | Size: 616 B |
Before Width: | Height: | Size: 495 B |
Before Width: | Height: | Size: 556 B |
Before Width: | Height: | Size: 143 B |
@ -1,16 +0,0 @@
|
||||
Minetest 0.4 mod: boats
|
||||
=======================
|
||||
by PilzAdam, slightly modified for NeXt
|
||||
|
||||
License of source code:
|
||||
-----------------------
|
||||
WTFPL
|
||||
|
||||
License of media (textures and sounds):
|
||||
---------------------------------------
|
||||
WTFPL
|
||||
|
||||
Authors of media files:
|
||||
-----------------------
|
||||
textures: Zeg9
|
||||
model: thetoon and Zeg9, modified by PavelS(SokolovPavel)
|
@ -1 +0,0 @@
|
||||
default
|
@ -1,217 +0,0 @@
|
||||
|
||||
--
|
||||
-- Helper functions
|
||||
--
|
||||
|
||||
local function is_water(pos)
|
||||
local nn = minetest.get_node(pos).name
|
||||
return minetest.get_item_group(nn, "water") ~= 0
|
||||
end
|
||||
|
||||
local function get_sign(i)
|
||||
if i == 0 then
|
||||
return 0
|
||||
else
|
||||
return i / math.abs(i)
|
||||
end
|
||||
end
|
||||
|
||||
local function get_velocity(v, yaw, y)
|
||||
local x = -math.sin(yaw) * v
|
||||
local z = math.cos(yaw) * v
|
||||
return {x = x, y = y, z = z}
|
||||
end
|
||||
|
||||
local function get_v(v)
|
||||
return math.sqrt(v.x ^ 2 + v.z ^ 2)
|
||||
end
|
||||
|
||||
--
|
||||
-- Boat entity
|
||||
--
|
||||
|
||||
local boat = {
|
||||
physical = true,
|
||||
collisionbox = {-0.5, -0.4, -0.5, 0.5, 0.3, 0.5},
|
||||
visual = "mesh",
|
||||
mesh = "boat.obj",
|
||||
textures = {"default_wood.png"},
|
||||
|
||||
driver = nil,
|
||||
v = 0,
|
||||
last_v = 0,
|
||||
removed = false
|
||||
}
|
||||
|
||||
function boat.on_rightclick(self, 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
|
||||
self.driver = nil
|
||||
clicker:set_detach()
|
||||
default.player_attached[name] = false
|
||||
default.player_set_animation(clicker, "stand" , 30)
|
||||
elseif not self.driver then
|
||||
self.driver = clicker
|
||||
clicker:set_attach(self.object, "", {x = 0, y = 11, z = -3}, {x = 0, y = 0, z = 0})
|
||||
default.player_attached[name] = true
|
||||
minetest.after(0.2, function()
|
||||
default.player_set_animation(clicker, "sit" , 30)
|
||||
end)
|
||||
self.object:setyaw(clicker:get_look_yaw() - math.pi / 2)
|
||||
end
|
||||
end
|
||||
|
||||
function boat.on_activate(self, staticdata, dtime_s)
|
||||
self.object:set_armor_groups({immortal = 1})
|
||||
if staticdata then
|
||||
self.v = tonumber(staticdata)
|
||||
end
|
||||
self.last_v = self.v
|
||||
end
|
||||
|
||||
function boat.get_staticdata(self)
|
||||
return tostring(self.v)
|
||||
end
|
||||
|
||||
function boat.on_punch(self, puncher, time_from_last_punch, tool_capabilities, direction)
|
||||
if not puncher or not puncher:is_player() or self.removed then
|
||||
return
|
||||
end
|
||||
if self.driver and puncher == self.driver then
|
||||
self.driver = nil
|
||||
puncher:set_detach()
|
||||
default.player_attached[puncher:get_player_name()] = false
|
||||
end
|
||||
if not self.driver then
|
||||
self.removed = true
|
||||
-- delay remove to ensure player is detached
|
||||
minetest.after(0.1, function()
|
||||
self.object:remove()
|
||||
end)
|
||||
if not minetest.setting_getbool("creative_mode") then
|
||||
puncher:get_inventory():add_item("main", "boats:boat")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function boat.on_step(self, dtime)
|
||||
self.v = get_v(self.object:getvelocity()) * get_sign(self.v)
|
||||
if self.driver then
|
||||
local ctrl = self.driver:get_player_control()
|
||||
local yaw = self.object:getyaw()
|
||||
if ctrl.up then
|
||||
self.v = self.v + 0.1
|
||||
elseif ctrl.down then
|
||||
self.v = self.v - 0.1
|
||||
end
|
||||
if ctrl.left then
|
||||
if self.v < 0 then
|
||||
self.object:setyaw(yaw - (1 + dtime) * 0.03)
|
||||
else
|
||||
self.object:setyaw(yaw + (1 + dtime) * 0.03)
|
||||
end
|
||||
elseif ctrl.right then
|
||||
if self.v < 0 then
|
||||
self.object:setyaw(yaw + (1 + dtime) * 0.03)
|
||||
else
|
||||
self.object:setyaw(yaw - (1 + dtime) * 0.03)
|
||||
end
|
||||
end
|
||||
end
|
||||
local velo = self.object:getvelocity()
|
||||
if self.v == 0 and velo.x == 0 and velo.y == 0 and velo.z == 0 then
|
||||
self.object:setpos(self.object:getpos())
|
||||
return
|
||||
end
|
||||
local s = get_sign(self.v)
|
||||
self.v = self.v - 0.02 * s
|
||||
if s ~= get_sign(self.v) then
|
||||
self.object:setvelocity({x = 0, y = 0, z = 0})
|
||||
self.v = 0
|
||||
return
|
||||
end
|
||||
if math.abs(self.v) > 4.5 then
|
||||
self.v = 4.5 * get_sign(self.v)
|
||||
end
|
||||
|
||||
local p = self.object:getpos()
|
||||
p.y = p.y - 0.5
|
||||
local new_velo = {x = 0, y = 0, z = 0}
|
||||
local new_acce = {x = 0, y = 0, z = 0}
|
||||
if not is_water(p) then
|
||||
local nodedef = minetest.registered_nodes[minetest.get_node(p).name]
|
||||
if (not nodedef) or nodedef.walkable then
|
||||
self.v = 0
|
||||
new_acce = {x = 0, y = 1, z = 0}
|
||||
else
|
||||
new_acce = {x = 0, y = -9.8, z = 0}
|
||||
end
|
||||
new_velo = get_velocity(self.v, self.object:getyaw(), self.object:getvelocity().y)
|
||||
self.object:setpos(self.object:getpos())
|
||||
else
|
||||
p.y = p.y + 1
|
||||
if is_water(p) then
|
||||
local y = self.object:getvelocity().y
|
||||
if y >= 4.5 then
|
||||
y = 4.5
|
||||
elseif y < 0 then
|
||||
new_acce = {x = 0, y = 20, z = 0}
|
||||
else
|
||||
new_acce = {x = 0, y = 5, z = 0}
|
||||
end
|
||||
new_velo = get_velocity(self.v, self.object:getyaw(), y)
|
||||
self.object:setpos(self.object:getpos())
|
||||
else
|
||||
new_acce = {x = 0, y = 0, z = 0}
|
||||
if math.abs(self.object:getvelocity().y) < 1 then
|
||||
local pos = self.object:getpos()
|
||||
pos.y = math.floor(pos.y) + 0.5
|
||||
self.object:setpos(pos)
|
||||
new_velo = get_velocity(self.v, self.object:getyaw(), 0)
|
||||
else
|
||||
new_velo = get_velocity(self.v, self.object:getyaw(), self.object:getvelocity().y)
|
||||
self.object:setpos(self.object:getpos())
|
||||
end
|
||||
end
|
||||
end
|
||||
self.object:setvelocity(new_velo)
|
||||
self.object:setacceleration(new_acce)
|
||||
end
|
||||
|
||||
minetest.register_entity("boats:boat", boat)
|
||||
|
||||
minetest.register_craftitem("boats:boat", {
|
||||
description = "Boat",
|
||||
inventory_image = "boat_inventory.png",
|
||||
wield_image = "boat_wield.png",
|
||||
wield_scale = {x = 2, y = 2, z = 1},
|
||||
liquids_pointable = true,
|
||||
|
||||
on_place = function(itemstack, placer, pointed_thing)
|
||||
if pointed_thing.type ~= "node" then
|
||||
return
|
||||
end
|
||||
if not is_water(pointed_thing.under) then
|
||||
return
|
||||
end
|
||||
pointed_thing.under.y = pointed_thing.under.y + 0.5
|
||||
minetest.add_entity(pointed_thing.under, "boats:boat")
|
||||
if not minetest.setting_getbool("creative_mode") then
|
||||
itemstack:take_item()
|
||||
end
|
||||
return itemstack
|
||||
end,
|
||||
})
|
||||
|
||||
minetest.register_craft({
|
||||
output = "boats:boat",
|
||||
recipe = {
|
||||
{"", "", "" },
|
||||
{"group:wood", "", "group:wood"},
|
||||
{"group:wood", "group:wood", "group:wood"},
|
||||
},
|
||||
})
|
||||
|
Before Width: | Height: | Size: 851 B |
Before Width: | Height: | Size: 546 B |
@ -1,17 +0,0 @@
|
||||
Minetest 0.4 mod: bones
|
||||
=======================
|
||||
|
||||
License of source code:
|
||||
-----------------------
|
||||
Copyright (C) 2012 PilzAdam
|
||||
|
||||
WTFPL
|
||||
|
||||
License of media (textures and sounds)
|
||||
--------------------------------------
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
|
||||
Authors of media files
|
||||
----------------------
|
||||
Bad_Command_
|
@ -1 +0,0 @@
|
||||
default
|
@ -1,219 +0,0 @@
|
||||
-- Minetest 0.4 mod: bones
|
||||
-- See README.txt for licensing and other information.
|
||||
|
||||
bones = {}
|
||||
|
||||
local function is_owner(pos, name)
|
||||
local owner = minetest.get_meta(pos):get_string("owner")
|
||||
if owner == "" or owner == name then
|
||||
return true
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
bones.bones_formspec =
|
||||
"size[8,9]"..
|
||||
default.gui_bg..
|
||||
default.gui_bg_img..
|
||||
default.gui_slots..
|
||||
"list[current_name;main;0,0.3;8,4;]"..
|
||||
"list[current_player;main;0,4.85;8,1;]"..
|
||||
"list[current_player;main;0,6.08;8,3;8]"..
|
||||
default.get_hotbar_bg(0,4.85)
|
||||
|
||||
local share_bones_time = tonumber(minetest.setting_get("share_bones_time") or 1200)
|
||||
local share_bones_time_early = tonumber(minetest.setting_get("share_bones_time_early") or (share_bones_time/4))
|
||||
|
||||
minetest.register_node("bones:bones", {
|
||||
description = "Bones",
|
||||
tiles = {
|
||||
"bones_top.png",
|
||||
"bones_bottom.png",
|
||||
"bones_side.png",
|
||||
"bones_side.png",
|
||||
"bones_rear.png",
|
||||
"bones_front.png"
|
||||
},
|
||||
paramtype2 = "facedir",
|
||||
groups = {dig_immediate=2},
|
||||
sounds = default.node_sound_dirt_defaults({
|
||||
footstep = {name="default_gravel_footstep", gain=0.5},
|
||||
dug = {name="default_gravel_footstep", gain=1.0},
|
||||
}),
|
||||
|
||||
can_dig = function(pos, player)
|
||||
local inv = minetest.get_meta(pos):get_inventory()
|
||||
return is_owner(pos, player:get_player_name()) and inv:is_empty("main")
|
||||
end,
|
||||
|
||||
allow_metadata_inventory_move = function(pos, from_list, from_index, to_list, to_index, count, player)
|
||||
if is_owner(pos, player:get_player_name()) then
|
||||
return count
|
||||
end
|
||||
return 0
|
||||
end,
|
||||
|
||||
allow_metadata_inventory_put = function(pos, listname, index, stack, player)
|
||||
return 0
|
||||
end,
|
||||
|
||||
allow_metadata_inventory_take = function(pos, listname, index, stack, player)
|
||||
if is_owner(pos, player:get_player_name()) then
|
||||
return stack:get_count()
|
||||
end
|
||||
return 0
|
||||
end,
|
||||
|
||||
on_metadata_inventory_take = function(pos, listname, index, stack, player)
|
||||
local meta = minetest.get_meta(pos)
|
||||
if meta:get_inventory():is_empty("main") then
|
||||
minetest.remove_node(pos)
|
||||
end
|
||||
end,
|
||||
|
||||
on_punch = function(pos, node, player)
|
||||
if(not is_owner(pos, player:get_player_name())) then
|
||||
return
|
||||
end
|
||||
|
||||
local inv = minetest.get_meta(pos):get_inventory()
|
||||
local player_inv = player:get_inventory()
|
||||
local has_space = true
|
||||
|
||||
for i=1,inv:get_size("main") do
|
||||
local stk = inv:get_stack("main", i)
|
||||
if player_inv:room_for_item("main", stk) then
|
||||
inv:set_stack("main", i, nil)
|
||||
player_inv:add_item("main", stk)
|
||||
else
|
||||
has_space = false
|
||||
break
|
||||
end
|
||||
end
|
||||
|
||||
-- remove bones if player emptied them
|
||||
if has_space then
|
||||
minetest.remove_node(pos)
|
||||
end
|
||||
end,
|
||||
|
||||
on_timer = function(pos, elapsed)
|
||||
local meta = minetest.get_meta(pos)
|
||||
local time = meta:get_int("time") + elapsed
|
||||
if time >= share_bones_time then
|
||||
meta:set_string("infotext", meta:get_string("owner").."'s old bones")
|
||||
meta:set_string("owner", "")
|
||||
else
|
||||
meta:set_int("time", time)
|
||||
return true
|
||||
end
|
||||
end,
|
||||
})
|
||||
|
||||
local function may_replace(pos, player)
|
||||
local node_name = minetest.get_node(pos).name
|
||||
local node_definition = minetest.registered_nodes[node_name]
|
||||
|
||||
-- if the node is unknown, we let the protection mod decide
|
||||
-- this is consistent with when a player could dig or not dig it
|
||||
-- unknown decoration would often be removed
|
||||
-- while unknown building materials in use would usually be left
|
||||
if not node_definition then
|
||||
-- only replace nodes that are not protected
|
||||
return not minetest.is_protected(pos, player:get_player_name())
|
||||
end
|
||||
|
||||
-- allow replacing air and liquids
|
||||
if node_name == "air" or node_definition.liquidtype ~= "none" then
|
||||
return true
|
||||
end
|
||||
|
||||
-- don't replace filled chests and other nodes that don't allow it
|
||||
local can_dig_func = node_definition.can_dig
|
||||
if can_dig_func and not can_dig_func(pos, player) then
|
||||
return false
|
||||
end
|
||||
|
||||
-- default to each nodes buildable_to; if a placed block would replace it, why shouldn't bones?
|
||||
-- flowers being squished by bones are more realistical than a squished stone, too
|
||||
-- exception are of course any protected buildable_to
|
||||
return node_definition.buildable_to and not minetest.is_protected(pos, player:get_player_name())
|
||||
end
|
||||
|
||||
minetest.register_on_dieplayer(function(player)
|
||||
if minetest.setting_getbool("creative_mode") then
|
||||
return
|
||||
end
|
||||
|
||||
local player_inv = player:get_inventory()
|
||||
if player_inv:is_empty("main") and
|
||||
player_inv:is_empty("craft") then
|
||||
return
|
||||
end
|
||||
|
||||
local pos = player:getpos()
|
||||
pos.x = math.floor(pos.x+0.5)
|
||||
pos.y = math.floor(pos.y+0.5)
|
||||
pos.z = math.floor(pos.z+0.5)
|
||||
local param2 = minetest.dir_to_facedir(player:get_look_dir())
|
||||
local player_name = player:get_player_name()
|
||||
local player_inv = player:get_inventory()
|
||||
|
||||
if (not may_replace(pos, player)) then
|
||||
if (may_replace({x=pos.x, y=pos.y+1, z=pos.z}, player)) then
|
||||
-- drop one node above if there's space
|
||||
-- this should solve most cases of protection related deaths in which players dig straight down
|
||||
-- yet keeps the bones reachable
|
||||
pos.y = pos.y+1
|
||||
else
|
||||
-- drop items instead of delete
|
||||
for i=1,player_inv:get_size("main") do
|
||||
minetest.add_item(pos, player_inv:get_stack("main", i))
|
||||
end
|
||||
for i=1,player_inv:get_size("craft") do
|
||||
minetest.add_item(pos, player_inv:get_stack("craft", i))
|
||||
end
|
||||
-- empty lists main and craft
|
||||
player_inv:set_list("main", {})
|
||||
player_inv:set_list("craft", {})
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
minetest.set_node(pos, {name="bones:bones", param2=param2})
|
||||
|
||||
local meta = minetest.get_meta(pos)
|
||||
local inv = meta:get_inventory()
|
||||
inv:set_size("main", 8*4)
|
||||
inv:set_list("main", player_inv:get_list("main"))
|
||||
|
||||
for i=1,player_inv:get_size("craft") do
|
||||
local stack = player_inv:get_stack("craft", i)
|
||||
if inv:room_for_item("main", stack) then
|
||||
inv:add_item("main", stack)
|
||||
else
|
||||
--drop if no space left
|
||||
minetest.add_item(pos, stack)
|
||||
end
|
||||
end
|
||||
|
||||
player_inv:set_list("main", {})
|
||||
player_inv:set_list("craft", {})
|
||||
|
||||
meta:set_string("formspec", bones.bones_formspec)
|
||||
meta:set_string("owner", player_name)
|
||||
|
||||
if share_bones_time ~= 0 then
|
||||
meta:set_string("infotext", player_name.."'s fresh bones")
|
||||
|
||||
if share_bones_time_early == 0 or not minetest.is_protected(pos, player_name) then
|
||||
meta:set_int("time", 0)
|
||||
else
|
||||
meta:set_int("time", (share_bones_time - share_bones_time_early))
|
||||
end
|
||||
|
||||
minetest.get_node_timer(pos):start(10)
|
||||
else
|
||||
meta:set_string("infotext", player_name.."'s bones")
|
||||
end
|
||||
end)
|
Before Width: | Height: | Size: 181 B |
Before Width: | Height: | Size: 183 B |
Before Width: | Height: | Size: 187 B |
Before Width: | Height: | Size: 188 B |
Before Width: | Height: | Size: 182 B |
@ -1,26 +0,0 @@
|
||||
Minetest 0.4 mod: bucket
|
||||
=========================
|
||||
|
||||
License of source code:
|
||||
-----------------------
|
||||
Copyright (C) 2011-2012 Kahrl <kahrl@gmx.net>
|
||||
Copyright (C) 2011-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
|
||||
License of media (textures and sounds)
|
||||
--------------------------------------
|
||||
Attribution-ShareAlike 3.0 Unported (CC BY-SA 3.0)
|
||||
http://creativecommons.org/licenses/by-sa/3.0/
|
||||
|
||||
Authors of media files
|
||||
-----------------------
|
||||
Everything not listed in here:
|
||||
Copyright (C) 2010-2012 celeron55, Perttu Ahola <celeron55@gmail.com>
|
||||
|
||||
|
@ -1,2 +0,0 @@
|
||||
default
|
||||
|
@ -1,192 +0,0 @@
|
||||
-- Minetest 0.4 mod: bucket
|
||||
-- See README.txt for licensing and other information.
|
||||
|
||||
minetest.register_alias("bucket", "bucket:bucket_empty")
|
||||
minetest.register_alias("bucket_water", "bucket:bucket_water")
|
||||
minetest.register_alias("bucket_lava", "bucket:bucket_lava")
|
||||
|
||||
minetest.register_craft({
|
||||
output = 'bucket:bucket_empty 1',
|
||||
recipe = {
|
||||
{'default:steel_ingot', '', 'default:steel_ingot'},
|
||||
{'', 'default:steel_ingot', ''},
|
||||
}
|
||||
})
|
||||
|
||||
bucket = {}
|
||||
bucket.liquids = {}
|
||||
|
||||
local function check_protection(pos, name, text)
|
||||
if minetest.is_protected(pos, name) then
|
||||
minetest.log("action", (name ~= "" and name or "A mod")
|
||||
.. " tried to " .. text
|
||||
.. " at protected position "
|
||||
.. minetest.pos_to_string(pos)
|
||||
.. " with a bucket")
|
||||
minetest.record_protection_violation(pos, name)
|
||||
return true
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
-- Register a new liquid
|
||||
-- source = name of the source node
|
||||
-- flowing = name of the flowing node
|
||||
-- itemname = name of the new bucket item (or nil if liquid is not takeable)
|
||||
-- inventory_image = texture of the new bucket item (ignored if itemname == nil)
|
||||
-- name = text description of the bucket item
|
||||
-- groups = (optional) groups of the bucket item, for example {water_bucket = 1}
|
||||
-- This function can be called from any mod (that depends on bucket).
|
||||
function bucket.register_liquid(source, flowing, itemname, inventory_image, name, groups)
|
||||
bucket.liquids[source] = {
|
||||
source = source,
|
||||
flowing = flowing,
|
||||
itemname = itemname,
|
||||
}
|
||||
bucket.liquids[flowing] = bucket.liquids[source]
|
||||
|
||||
if itemname ~= nil then
|
||||
minetest.register_craftitem(itemname, {
|
||||
description = name,
|
||||
inventory_image = inventory_image,
|
||||
stack_max = 1,
|
||||
liquids_pointable = true,
|
||||
groups = groups,
|
||||
on_place = function(itemstack, user, pointed_thing)
|
||||
-- Must be pointing to node
|
||||
if pointed_thing.type ~= "node" then
|
||||
return
|
||||
end
|
||||
|
||||
local node = minetest.get_node_or_nil(pointed_thing.under)
|
||||
local ndef
|
||||
if node then
|
||||
ndef = minetest.registered_nodes[node.name]
|
||||
end
|
||||
-- Call on_rightclick if the pointed node defines it
|
||||
if ndef and ndef.on_rightclick and
|
||||
user and not user:get_player_control().sneak then
|
||||
return ndef.on_rightclick(
|
||||
pointed_thing.under,
|
||||
node, user,
|
||||
itemstack) or itemstack
|
||||
end
|
||||
|
||||
local place_liquid = function(pos, node, source, flowing)
|
||||
if check_protection(pos,
|
||||
user and user:get_player_name() or "",
|
||||
"place "..source) then
|
||||
return
|
||||
end
|
||||
minetest.add_node(pos, {name=source})
|
||||
end
|
||||
|
||||
-- Check if pointing to a buildable node
|
||||
if ndef and ndef.buildable_to then
|
||||
-- buildable; replace the node
|
||||
place_liquid(pointed_thing.under, node,
|
||||
source, flowing)
|
||||
else
|
||||
-- not buildable to; place the liquid above
|
||||
-- check if the node above can be replaced
|
||||
local node = minetest.get_node_or_nil(pointed_thing.above)
|
||||
if node and minetest.registered_nodes[node.name].buildable_to then
|
||||
place_liquid(pointed_thing.above,
|
||||
node, source,
|
||||
flowing)
|
||||
else
|
||||
-- do not remove the bucket with the liquid
|
||||
return
|
||||
end
|
||||
end
|
||||
return {name="bucket:bucket_empty"}
|
||||
end
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
minetest.register_craftitem("bucket:bucket_empty", {
|
||||
description = "Empty Bucket",
|
||||
inventory_image = "bucket.png",
|
||||
stack_max = 99,
|
||||
liquids_pointable = true,
|
||||
on_use = function(itemstack, user, pointed_thing)
|
||||
-- Must be pointing to node
|
||||
if pointed_thing.type ~= "node" then
|
||||
return
|
||||
end
|
||||
-- Check if pointing to a liquid source
|
||||
local node = minetest.get_node(pointed_thing.under)
|
||||
local liquiddef = bucket.liquids[node.name]
|
||||
local item_count = user:get_wielded_item():get_count()
|
||||
|
||||
if liquiddef ~= nil
|
||||
and liquiddef.itemname ~= nil
|
||||
and node.name == liquiddef.source then
|
||||
if check_protection(pointed_thing.under,
|
||||
user:get_player_name(),
|
||||
"take ".. node.name) then
|
||||
return
|
||||
end
|
||||
|
||||
-- default set to return filled bucket
|
||||
local giving_back = liquiddef.itemname
|
||||
|
||||
-- check if holding more than 1 empty bucket
|
||||
if item_count > 1 then
|
||||
|
||||
-- if space in inventory add filled bucked, otherwise drop as item
|
||||
local inv = user:get_inventory()
|
||||
if inv:room_for_item("main", {name=liquiddef.itemname}) then
|
||||
inv:add_item("main", liquiddef.itemname)
|
||||
else
|
||||
local pos = user:getpos()
|
||||
pos.y = math.floor(pos.y + 0.5)
|
||||
core.add_item(pos, liquiddef.itemname)
|
||||
end
|
||||
|
||||
-- set to return empty buckets minus 1
|
||||
giving_back = "bucket:bucket_empty "..tostring(item_count-1)
|
||||
|
||||
end
|
||||
|
||||
minetest.add_node(pointed_thing.under, {name="air"})
|
||||
|
||||
return ItemStack(giving_back)
|
||||
end
|
||||
end,
|
||||
})
|
||||
|
||||
bucket.register_liquid(
|
||||
"default:water_source",
|
||||
"default:water_flowing",
|
||||
"bucket:bucket_water",
|
||||
"bucket_water.png",
|
||||
"Water Bucket",
|
||||
{water_bucket = 1}
|
||||
)
|
||||
|
||||
bucket.register_liquid(
|
||||
"default:river_water_source",
|
||||
"default:river_water_flowing",
|
||||
"bucket:bucket_river_water",
|
||||
"bucket_river_water.png",
|
||||
"River Water Bucket",
|
||||
{water_bucket = 1}
|
||||
)
|
||||
|
||||
bucket.register_liquid(
|
||||
"default:lava_source",
|
||||
"default:lava_flowing",
|
||||
"bucket:bucket_lava",
|
||||
"bucket_lava.png",
|
||||
"Lava Bucket"
|
||||
)
|
||||
|
||||
minetest.register_craft({
|
||||
type = "fuel",
|
||||
recipe = "bucket:bucket_lava",
|
||||
burntime = 60,
|
||||
replacements = {{"bucket:bucket_lava", "bucket:bucket_empty"}},
|
||||
})
|
||||
|
Before Width: | Height: | Size: 163 B |
Before Width: | Height: | Size: 167 B |
Before Width: | Height: | Size: 316 B |
Before Width: | Height: | Size: 169 B |