]> git.lizzy.rs Git - dragonfireclient.git/blob - src/script/cpp_api/s_nodemeta.cpp
01eee337c5540ad34da6b781658cf66541c7c40b
[dragonfireclient.git] / src / script / cpp_api / s_nodemeta.cpp
1 /*
2 Minetest
3 Copyright (C) 2013 celeron55, Perttu Ahola <celeron55@gmail.com>
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU Lesser General Public License as published by
7 the Free Software Foundation; either version 2.1 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 GNU Lesser General Public License for more details.
14
15 You should have received a copy of the GNU Lesser General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #include "cpp_api/s_nodemeta.h"
21 #include "cpp_api/s_internal.h"
22 #include "common/c_converter.h"
23 #include "nodedef.h"
24 #include "mapnode.h"
25 #include "server.h"
26 #include "environment.h"
27 #include "lua_api/l_item.h"
28
29 // Return number of accepted items to be moved
30 int ScriptApiNodemeta::nodemeta_inventory_AllowMove(v3s16 p,
31                 const std::string &from_list, int from_index,
32                 const std::string &to_list, int to_index,
33                 int count, ServerActiveObject *player)
34 {
35         SCRIPTAPI_PRECHECKHEADER
36
37         INodeDefManager *ndef = getServer()->ndef();
38
39         // If node doesn't exist, we don't know what callback to call
40         MapNode node = getEnv()->getMap().getNodeNoEx(p);
41         if (node.getContent() == CONTENT_IGNORE)
42                 return 0;
43
44         // Push callback function on stack
45         std::string nodename = ndef->get(node).name;
46         if (!getItemCallback(nodename.c_str(), "allow_metadata_inventory_move"))
47                 return count;
48
49         // function(pos, from_list, from_index, to_list, to_index, count, player)
50         push_v3s16(L, p);                     // pos
51         lua_pushstring(L, from_list.c_str()); // from_list
52         lua_pushinteger(L, from_index + 1);   // from_index
53         lua_pushstring(L, to_list.c_str());   // to_list
54         lua_pushinteger(L, to_index + 1);     // to_index
55         lua_pushinteger(L, count);            // count
56         objectrefGetOrCreate(L, player);      // player
57         if (lua_pcall(L, 7, 1, m_errorhandler))
58                 scriptError();
59         if (!lua_isnumber(L, -1))
60                 throw LuaError("allow_metadata_inventory_move should"
61                                 " return a number, guilty node: " + nodename);
62         int num = luaL_checkinteger(L, -1);
63         lua_pop(L, 1); // Pop integer
64         return num;
65 }
66
67 // Return number of accepted items to be put
68 int ScriptApiNodemeta::nodemeta_inventory_AllowPut(v3s16 p,
69                 const std::string &listname, int index, ItemStack &stack,
70                 ServerActiveObject *player)
71 {
72         SCRIPTAPI_PRECHECKHEADER
73
74         INodeDefManager *ndef = getServer()->ndef();
75
76         // If node doesn't exist, we don't know what callback to call
77         MapNode node = getEnv()->getMap().getNodeNoEx(p);
78         if (node.getContent() == CONTENT_IGNORE)
79                 return 0;
80
81         // Push callback function on stack
82         std::string nodename = ndef->get(node).name;
83         if (!getItemCallback(nodename.c_str(), "allow_metadata_inventory_put"))
84                 return stack.count;
85
86         // Call function(pos, listname, index, stack, player)
87         push_v3s16(L, p);                    // pos
88         lua_pushstring(L, listname.c_str()); // listname
89         lua_pushinteger(L, index + 1);       // index
90         LuaItemStack::create(L, stack);      // stack
91         objectrefGetOrCreate(L, player);     // player
92         if (lua_pcall(L, 5, 1, m_errorhandler))
93                 scriptError();
94         if(!lua_isnumber(L, -1))
95                 throw LuaError("allow_metadata_inventory_put should"
96                                 " return a number, guilty node: " + nodename);
97         int num = luaL_checkinteger(L, -1);
98         lua_pop(L, 1); // Pop integer
99         return num;
100 }
101
102 // Return number of accepted items to be taken
103 int ScriptApiNodemeta::nodemeta_inventory_AllowTake(v3s16 p,
104                 const std::string &listname, int index, ItemStack &stack,
105                 ServerActiveObject *player)
106 {
107         SCRIPTAPI_PRECHECKHEADER
108
109         INodeDefManager *ndef = getServer()->ndef();
110
111         // If node doesn't exist, we don't know what callback to call
112         MapNode node = getEnv()->getMap().getNodeNoEx(p);
113         if (node.getContent() == CONTENT_IGNORE)
114                 return 0;
115
116         // Push callback function on stack
117         std::string nodename = ndef->get(node).name;
118         if (!getItemCallback(nodename.c_str(), "allow_metadata_inventory_take"))
119                 return stack.count;
120
121         // Call function(pos, listname, index, count, player)
122         push_v3s16(L, p);                    // pos
123         lua_pushstring(L, listname.c_str()); // listname
124         lua_pushinteger(L, index + 1);       // index
125         LuaItemStack::create(L, stack);      // stack
126         objectrefGetOrCreate(L, player);     // player
127         if (lua_pcall(L, 5, 1, m_errorhandler))
128                 scriptError();
129         if (!lua_isnumber(L, -1))
130                 throw LuaError("allow_metadata_inventory_take should"
131                                 " return a number, guilty node: " + nodename);
132         int num = luaL_checkinteger(L, -1);
133         lua_pop(L, 1); // Pop integer
134         return num;
135 }
136
137 // Report moved items
138 void ScriptApiNodemeta::nodemeta_inventory_OnMove(v3s16 p,
139                 const std::string &from_list, int from_index,
140                 const std::string &to_list, int to_index,
141                 int count, ServerActiveObject *player)
142 {
143         SCRIPTAPI_PRECHECKHEADER
144
145         INodeDefManager *ndef = getServer()->ndef();
146
147         // If node doesn't exist, we don't know what callback to call
148         MapNode node = getEnv()->getMap().getNodeNoEx(p);
149         if (node.getContent() == CONTENT_IGNORE)
150                 return;
151
152         // Push callback function on stack
153         std::string nodename = ndef->get(node).name;
154         if (!getItemCallback(nodename.c_str(), "on_metadata_inventory_move"))
155                 return;
156
157         // function(pos, from_list, from_index, to_list, to_index, count, player)
158         push_v3s16(L, p);                     // pos
159         lua_pushstring(L, from_list.c_str()); // from_list
160         lua_pushinteger(L, from_index + 1);   // from_index
161         lua_pushstring(L, to_list.c_str());   // to_list
162         lua_pushinteger(L, to_index + 1);     // to_index
163         lua_pushinteger(L, count);            // count
164         objectrefGetOrCreate(L, player);      // player
165         if (lua_pcall(L, 7, 0, m_errorhandler))
166                 scriptError();
167 }
168
169 // Report put items
170 void ScriptApiNodemeta::nodemeta_inventory_OnPut(v3s16 p,
171                 const std::string &listname, int index, ItemStack &stack,
172                 ServerActiveObject *player)
173 {
174         SCRIPTAPI_PRECHECKHEADER
175
176         INodeDefManager *ndef = getServer()->ndef();
177
178         // If node doesn't exist, we don't know what callback to call
179         MapNode node = getEnv()->getMap().getNodeNoEx(p);
180         if (node.getContent() == CONTENT_IGNORE)
181                 return;
182
183         // Push callback function on stack
184         std::string nodename = ndef->get(node).name;
185         if (!getItemCallback(nodename.c_str(), "on_metadata_inventory_put"))
186                 return;
187
188         // Call function(pos, listname, index, stack, player)
189         push_v3s16(L, p);                    // pos
190         lua_pushstring(L, listname.c_str()); // listname
191         lua_pushinteger(L, index + 1);       // index
192         LuaItemStack::create(L, stack);      // stack
193         objectrefGetOrCreate(L, player);     // player
194         if (lua_pcall(L, 5, 0, m_errorhandler))
195                 scriptError();
196 }
197
198 // Report taken items
199 void ScriptApiNodemeta::nodemeta_inventory_OnTake(v3s16 p,
200                 const std::string &listname, int index, ItemStack &stack,
201                 ServerActiveObject *player)
202 {
203         SCRIPTAPI_PRECHECKHEADER
204
205         INodeDefManager *ndef = getServer()->ndef();
206
207         // If node doesn't exist, we don't know what callback to call
208         MapNode node = getEnv()->getMap().getNodeNoEx(p);
209         if (node.getContent() == CONTENT_IGNORE)
210                 return;
211
212         // Push callback function on stack
213         std::string nodename = ndef->get(node).name;
214         if (!getItemCallback(nodename.c_str(), "on_metadata_inventory_take"))
215                 return;
216
217         // Call function(pos, listname, index, stack, player)
218         push_v3s16(L, p);                    // pos
219         lua_pushstring(L, listname.c_str()); // listname
220         lua_pushinteger(L, index + 1);       // index
221         LuaItemStack::create(L, stack);      // stack
222         objectrefGetOrCreate(L, player);     // player
223         if (lua_pcall(L, 5, 0, m_errorhandler))
224                 scriptError();
225 }
226
227 ScriptApiNodemeta::ScriptApiNodemeta() {
228 }
229
230 ScriptApiNodemeta::~ScriptApiNodemeta() {
231 }
232