doors_chest.lua 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791
  1. -- Since the doors mod has changed in the latest daily builds I have taken the
  2. -- WTFPL licenced code from the old doors mod and included an edited version
  3. -- within this mod for local use.
  4. local S = protector.intllib
  5. local F = minetest.formspec_escape
  6. -- MineClone2 support
  7. local mcl = minetest.get_modpath("mcl_core")
  8. local mcf = minetest.get_modpath("mcl_formspec")
  9. -- Are crafts enabled?
  10. local protector_crafts = minetest.settings:get_bool("protector_crafts") ~= false
  11. -- Registers a door
  12. function register_door(name, def)
  13. def.groups.not_in_creative_inventory = 1
  14. local box = {{-0.5, -0.5, -0.5, 0.5, 0.5, -0.5+1.5/16}}
  15. def.node_box_bottom = box
  16. def.node_box_top = box
  17. def.selection_box_bottom = box
  18. def.selection_box_top = box
  19. def.sound_close_door = "doors_door_close"
  20. def.sound_open_door = "doors_door_open"
  21. minetest.register_craftitem(name, {
  22. description = def.description,
  23. inventory_image = def.inventory_image,
  24. on_place = function(itemstack, placer, pointed_thing)
  25. if not pointed_thing.type == "node" then
  26. return itemstack
  27. end
  28. local ptu = pointed_thing.under
  29. local nu = minetest.get_node(ptu)
  30. if minetest.registered_nodes[nu.name]
  31. and minetest.registered_nodes[nu.name].on_rightclick then
  32. return minetest.registered_nodes[nu.name].on_rightclick(ptu, nu, placer, itemstack)
  33. end
  34. local pt = pointed_thing.above
  35. local pt2 = {x=pt.x, y=pt.y, z=pt.z}
  36. pt2.y = pt2.y+1
  37. if
  38. not minetest.registered_nodes[minetest.get_node(pt).name].buildable_to or
  39. not minetest.registered_nodes[minetest.get_node(pt2).name].buildable_to or
  40. not placer or
  41. not placer:is_player()
  42. then
  43. return itemstack
  44. end
  45. if minetest.is_protected(pt, placer:get_player_name()) or
  46. minetest.is_protected(pt2, placer:get_player_name()) then
  47. minetest.record_protection_violation(pt, placer:get_player_name())
  48. return itemstack
  49. end
  50. local p2 = minetest.dir_to_facedir(placer:get_look_dir())
  51. local pt3 = {x=pt.x, y=pt.y, z=pt.z}
  52. if p2 == 0 then
  53. pt3.x = pt3.x-1
  54. elseif p2 == 1 then
  55. pt3.z = pt3.z+1
  56. elseif p2 == 2 then
  57. pt3.x = pt3.x+1
  58. elseif p2 == 3 then
  59. pt3.z = pt3.z-1
  60. end
  61. if minetest.get_item_group(minetest.get_node(pt3).name, "door") == 0 then
  62. minetest.set_node(pt, {name=name.."_b_1", param2=p2})
  63. minetest.set_node(pt2, {name=name.."_t_1", param2=p2})
  64. else
  65. minetest.set_node(pt, {name=name.."_b_2", param2=p2})
  66. minetest.set_node(pt2, {name=name.."_t_2", param2=p2})
  67. minetest.get_meta(pt):set_int("right", 1)
  68. minetest.get_meta(pt2):set_int("right", 1)
  69. end
  70. if not minetest.settings:get_bool("creative_mode") then
  71. itemstack:take_item()
  72. end
  73. return itemstack
  74. end,
  75. })
  76. local tt = def.tiles_top
  77. local tb = def.tiles_bottom
  78. local function after_dig_node(pos, name, digger)
  79. local node = minetest.get_node(pos)
  80. if node.name == name then
  81. minetest.node_dig(pos, node, digger)
  82. end
  83. end
  84. local function on_rightclick(pos, dir, check_name, replace, replace_dir, params)
  85. pos.y = pos.y+dir
  86. if minetest.get_node(pos).name ~= check_name then
  87. return
  88. end
  89. local p2 = minetest.get_node(pos).param2
  90. p2 = params[p2+1]
  91. minetest.swap_node(pos, {name=replace_dir, param2=p2})
  92. pos.y = pos.y-dir
  93. minetest.swap_node(pos, {name=replace, param2=p2})
  94. local snd_1 = def.sound_close_door
  95. local snd_2 = def.sound_open_door
  96. if params[1] == 3 then
  97. snd_1 = def.sound_open_door
  98. snd_2 = def.sound_close_door
  99. end
  100. if minetest.get_meta(pos):get_int("right") ~= 0 then
  101. minetest.sound_play(snd_1, {pos = pos, gain = 0.3, max_hear_distance = 10})
  102. else
  103. minetest.sound_play(snd_2, {pos = pos, gain = 0.3, max_hear_distance = 10})
  104. end
  105. end
  106. local function on_rotate(pos, node, dir, user, check_name, mode, new_param2)
  107. if mode ~= screwdriver.ROTATE_FACE then
  108. return false
  109. end
  110. pos.y = pos.y + dir
  111. if not minetest.get_node(pos).name == check_name then
  112. return false
  113. end
  114. if minetest.is_protected(pos, user:get_player_name()) then
  115. minetest.record_protection_violation(pos, user:get_player_name())
  116. return false
  117. end
  118. local node2 = minetest.get_node(pos)
  119. node2.param2 = (node2.param2 + 1) % 4
  120. minetest.swap_node(pos, node2)
  121. pos.y = pos.y - dir
  122. node.param2 = (node.param2 + 1) % 4
  123. minetest.swap_node(pos, node)
  124. return true
  125. end
  126. minetest.register_node(name.."_b_1", {
  127. tiles = {tb[2], tb[2], tb[2], tb[2], tb[1], tb[1].."^[transformfx"},
  128. paramtype = "light",
  129. paramtype2 = "facedir",
  130. use_texture_alpha = "clip",
  131. is_ground_content = false,
  132. drop = name,
  133. drawtype = "nodebox",
  134. node_box = {
  135. type = "fixed",
  136. fixed = def.node_box_bottom
  137. },
  138. selection_box = {
  139. type = "fixed",
  140. fixed = def.selection_box_bottom
  141. },
  142. groups = def.groups,
  143. after_dig_node = function(pos, oldnode, oldmetadata, digger)
  144. pos.y = pos.y+1
  145. after_dig_node(pos, name.."_t_1", digger)
  146. end,
  147. on_rightclick = function(pos, node, clicker)
  148. if not minetest.is_protected(pos, clicker:get_player_name()) then
  149. on_rightclick(pos, 1, name.."_t_1", name.."_b_2", name.."_t_2", {1,2,3,0})
  150. end
  151. end,
  152. on_rotate = function(pos, node, user, mode, new_param2)
  153. return on_rotate(pos, node, 1, user, name.."_t_1", mode)
  154. end,
  155. sounds = def.sounds,
  156. sunlight_propagates = def.sunlight,
  157. on_blast = function() end,
  158. })
  159. minetest.register_node(name.."_t_1", {
  160. tiles = {tt[2], tt[2], tt[2], tt[2], tt[1], tt[1].."^[transformfx"},
  161. paramtype = "light",
  162. paramtype2 = "facedir",
  163. use_texture_alpha = "clip",
  164. is_ground_content = false,
  165. drop = "",
  166. drawtype = "nodebox",
  167. node_box = {
  168. type = "fixed",
  169. fixed = def.node_box_top
  170. },
  171. selection_box = {
  172. type = "fixed",
  173. fixed = def.selection_box_top
  174. },
  175. groups = def.groups,
  176. after_dig_node = function(pos, oldnode, oldmetadata, digger)
  177. pos.y = pos.y-1
  178. after_dig_node(pos, name.."_b_1", digger)
  179. end,
  180. on_rightclick = function(pos, node, clicker)
  181. if not minetest.is_protected(pos, clicker:get_player_name()) then
  182. on_rightclick(pos, -1, name.."_b_1", name.."_t_2", name.."_b_2", {1,2,3,0})
  183. end
  184. end,
  185. on_rotate = function(pos, node, user, mode, new_param2)
  186. return on_rotate(pos, node, -1, user, name.."_b_1", mode)
  187. end,
  188. sounds = def.sounds,
  189. sunlight_propagates = def.sunlight,
  190. on_blast = function() end,
  191. })
  192. minetest.register_node(name.."_b_2", {
  193. tiles = {tb[2], tb[2], tb[2], tb[2], tb[1].."^[transformfx", tb[1]},
  194. paramtype = "light",
  195. paramtype2 = "facedir",
  196. use_texture_alpha = "clip",
  197. is_ground_content = false,
  198. drop = name,
  199. drawtype = "nodebox",
  200. node_box = {
  201. type = "fixed",
  202. fixed = def.node_box_bottom
  203. },
  204. selection_box = {
  205. type = "fixed",
  206. fixed = def.selection_box_bottom
  207. },
  208. groups = def.groups,
  209. after_dig_node = function(pos, oldnode, oldmetadata, digger)
  210. pos.y = pos.y+1
  211. after_dig_node(pos, name.."_t_2", digger)
  212. end,
  213. on_rightclick = function(pos, node, clicker)
  214. if not minetest.is_protected(pos, clicker:get_player_name()) then
  215. on_rightclick(pos, 1, name.."_t_2", name.."_b_1", name.."_t_1", {3,0,1,2})
  216. end
  217. end,
  218. on_rotate = function(pos, node, user, mode, new_param2)
  219. return on_rotate(pos, node, 1, user, name.."_t_2", mode)
  220. end,
  221. sounds = def.sounds,
  222. sunlight_propagates = def.sunlight,
  223. on_blast = function() end,
  224. })
  225. minetest.register_node(name.."_t_2", {
  226. tiles = {tt[2], tt[2], tt[2], tt[2], tt[1].."^[transformfx", tt[1]},
  227. paramtype = "light",
  228. paramtype2 = "facedir",
  229. use_texture_alpha = "clip",
  230. is_ground_content = false,
  231. drop = "",
  232. drawtype = "nodebox",
  233. node_box = {
  234. type = "fixed",
  235. fixed = def.node_box_top
  236. },
  237. selection_box = {
  238. type = "fixed",
  239. fixed = def.selection_box_top
  240. },
  241. groups = def.groups,
  242. after_dig_node = function(pos, oldnode, oldmetadata, digger)
  243. pos.y = pos.y-1
  244. after_dig_node(pos, name.."_b_2", digger)
  245. end,
  246. on_rightclick = function(pos, node, clicker)
  247. if not minetest.is_protected(pos, clicker:get_player_name()) then
  248. on_rightclick(pos, -1, name.."_b_2", name.."_t_1", name.."_b_1", {3,0,1,2})
  249. end
  250. end,
  251. on_rotate = function(pos, node, user, mode, new_param2)
  252. return on_rotate(pos, node, -1, user, name.."_b_2", mode)
  253. end,
  254. sounds = def.sounds,
  255. sunlight_propagates = def.sunlight,
  256. on_blast = function() end,
  257. })
  258. end
  259. -- Protected Wooden Door
  260. local name = "protector:door_wood"
  261. register_door(name, {
  262. description = S("Protected Wooden Door"),
  263. inventory_image = "doors_wood.png^protector_logo.png",
  264. groups = {
  265. snappy = 1, choppy = 2, dig_immediate = 2,
  266. unbreakable = 1, --door = 1
  267. },
  268. tiles_bottom = {"doors_wood_b.png^protector_logo.png", "doors_brown.png"},
  269. tiles_top = {"doors_wood_a.png", "doors_brown.png"},
  270. sounds = default.node_sound_wood_defaults(),
  271. sunlight = false
  272. })
  273. if protector_crafts then
  274. if mcl then
  275. minetest.register_craft({
  276. output = name,
  277. recipe = {
  278. {"mcl_doors:wooden_door", "mcl_core:gold_ingot"}
  279. }
  280. })
  281. else
  282. minetest.register_craft({
  283. output = name,
  284. recipe = {
  285. {"group:wood", "group:wood"},
  286. {"group:wood", "default:copper_ingot"},
  287. {"group:wood", "group:wood"}
  288. }
  289. })
  290. minetest.register_craft({
  291. output = name,
  292. recipe = {
  293. {"doors:door_wood", "default:copper_ingot"}
  294. }
  295. })
  296. end
  297. end
  298. -- Protected Steel Door
  299. local name = "protector:door_steel"
  300. register_door(name, {
  301. description = S("Protected Steel Door"),
  302. inventory_image = "doors_steel.png^protector_logo.png",
  303. groups = {
  304. snappy = 1, bendy = 2, cracky = 1,
  305. level = 2, unbreakable = 1, -- door = 1
  306. },
  307. tiles_bottom = {"doors_steel_b.png^protector_logo.png", "doors_grey.png"},
  308. tiles_top = {"doors_steel_a.png", "doors_grey.png"},
  309. sounds = default.node_sound_wood_defaults(),
  310. sunlight = false,
  311. })
  312. if protector_crafts then
  313. if mcl then
  314. minetest.register_craft({
  315. output = name,
  316. recipe = {
  317. {"mcl_doors:iron_door", "mcl_core:gold_ingot"}
  318. }
  319. })
  320. else
  321. minetest.register_craft({
  322. output = name,
  323. recipe = {
  324. {"default:steel_ingot", "default:steel_ingot"},
  325. {"default:steel_ingot", "default:copper_ingot"},
  326. {"default:steel_ingot", "default:steel_ingot"}
  327. }
  328. })
  329. minetest.register_craft({
  330. output = name,
  331. recipe = {
  332. {"doors:door_steel", "default:copper_ingot"}
  333. }
  334. })
  335. end
  336. end
  337. ----trapdoor----
  338. function register_trapdoor(name, def)
  339. local name_closed = name
  340. local name_opened = name.."_open"
  341. def.on_rightclick = function (pos, node, clicker, itemstack, pointed_thing)
  342. if minetest.is_protected(pos, clicker:get_player_name()) then
  343. return
  344. end
  345. local newname = node.name == name_closed and name_opened or name_closed
  346. local sound = false
  347. if node.name == name_closed then sound = "doors_door_open" end
  348. if node.name == name_opened then sound = "doors_door_close" end
  349. if sound then
  350. minetest.sound_play(sound, {pos = pos, gain = 0.3, max_hear_distance = 10})
  351. end
  352. minetest.swap_node(pos, {name = newname, param1 = node.param1, param2 = node.param2})
  353. end
  354. -- Common trapdoor configuration
  355. def.drawtype = "nodebox"
  356. def.paramtype = "light"
  357. def.paramtype2 = "facedir"
  358. def.use_texture_alpha = "clip"
  359. def.is_ground_content = false
  360. local def_opened = table.copy(def)
  361. local def_closed = table.copy(def)
  362. def_closed.node_box = {
  363. type = "fixed",
  364. fixed = {-0.5, -0.5, -0.5, 0.5, -6/16, 0.5}
  365. }
  366. def_closed.selection_box = {
  367. type = "fixed",
  368. fixed = {-0.5, -0.5, -0.5, 0.5, -6/16, 0.5}
  369. }
  370. def_closed.tiles = { def.tile_front, def.tile_front, def.tile_side, def.tile_side,
  371. def.tile_side, def.tile_side }
  372. def_opened.node_box = {
  373. type = "fixed",
  374. fixed = {-0.5, -0.5, 6/16, 0.5, 0.5, 0.5}
  375. }
  376. def_opened.selection_box = {
  377. type = "fixed",
  378. fixed = {-0.5, -0.5, 6/16, 0.5, 0.5, 0.5}
  379. }
  380. def_opened.tiles = { def.tile_side, def.tile_side,
  381. def.tile_side .. "^[transform3",
  382. def.tile_side .. "^[transform1",
  383. def.tile_front, def.tile_front }
  384. def_opened.drop = name_closed
  385. def_opened.groups.not_in_creative_inventory = 1
  386. minetest.register_node(name_opened, def_opened)
  387. minetest.register_node(name_closed, def_closed)
  388. end
  389. -- Protected Wooden Trapdoor
  390. register_trapdoor("protector:trapdoor", {
  391. description = S("Protected Trapdoor"),
  392. inventory_image = "doors_trapdoor.png^protector_logo.png",
  393. wield_image = "doors_trapdoor.png^protector_logo.png",
  394. tile_front = "doors_trapdoor.png^protector_logo.png",
  395. tile_side = "doors_trapdoor_side.png",
  396. groups = {
  397. snappy = 1, choppy = 2, dig_immediate = 2,
  398. unbreakable = 1, --door = 1
  399. },
  400. sounds = default.node_sound_wood_defaults(),
  401. })
  402. if protector_crafts then
  403. if mcl then
  404. minetest.register_craft({
  405. output = "protector:trapdoor",
  406. recipe = {
  407. {"mcl_doors:trapdoor", "mcl_core:gold_ingot"}
  408. }
  409. })
  410. else
  411. minetest.register_craft({
  412. output = "protector:trapdoor 2",
  413. recipe = {
  414. {"group:wood", "default:copper_ingot", "group:wood"},
  415. {"group:wood", "group:wood", "group:wood"}
  416. }
  417. })
  418. minetest.register_craft({
  419. output = "protector:trapdoor",
  420. recipe = {
  421. {"doors:trapdoor", "default:copper_ingot"}
  422. }
  423. })
  424. end
  425. end
  426. -- Protected Steel Trapdoor
  427. register_trapdoor("protector:trapdoor_steel", {
  428. description = S("Protected Steel Trapdoor"),
  429. inventory_image = "doors_trapdoor_steel.png^protector_logo.png",
  430. wield_image = "doors_trapdoor_steel.png^protector_logo.png",
  431. tile_front = "doors_trapdoor_steel.png^protector_logo.png",
  432. tile_side = "doors_trapdoor_steel_side.png",
  433. groups = {
  434. snappy = 1, bendy = 2, cracky = 1, melty = 2, level = 2,
  435. unbreakable = 1, --door = 1
  436. },
  437. sounds = default.node_sound_wood_defaults(),
  438. })
  439. if protector_crafts then
  440. if mcl then
  441. minetest.register_craft({
  442. output = "protector:trapdoor_steel",
  443. recipe = {
  444. {"mcl_doors:iron_trapdoor", "mcl_core:gold_ingot"}
  445. }
  446. })
  447. else
  448. minetest.register_craft({
  449. output = "protector:trapdoor_steel",
  450. recipe = {
  451. {"default:copper_ingot", "default:steel_ingot"},
  452. {"default:steel_ingot", "default:steel_ingot"}
  453. }
  454. })
  455. minetest.register_craft({
  456. output = "protector:trapdoor_steel",
  457. recipe = {
  458. {"doors:trapdoor_steel", "default:copper_ingot"}
  459. }
  460. })
  461. end
  462. end
  463. -- Protected Chest
  464. minetest.register_node("protector:chest", {
  465. description = S("Protected Chest"),
  466. tiles = {
  467. "default_chest_top.png", "default_chest_top.png",
  468. "default_chest_side.png", "default_chest_side.png",
  469. "default_chest_side.png", "default_chest_front.png^protector_logo.png"
  470. },
  471. paramtype2 = "facedir",
  472. groups = {dig_immediate = 2, unbreakable = 1},
  473. legacy_facedir_simple = true,
  474. is_ground_content = false,
  475. sounds = default.node_sound_wood_defaults(),
  476. on_construct = function(pos)
  477. local meta = minetest.get_meta(pos)
  478. local inv = meta:get_inventory()
  479. meta:set_string("infotext", S("Protected Chest"))
  480. meta:set_string("name", S("Protected Chest"))
  481. inv:set_size("main", 8 * 4)
  482. end,
  483. can_dig = function(pos,player)
  484. local meta = minetest.get_meta(pos)
  485. local inv = meta:get_inventory()
  486. if inv:is_empty("main") then
  487. if not minetest.is_protected(pos, player:get_player_name()) then
  488. return true
  489. end
  490. end
  491. end,
  492. on_metadata_inventory_put = function(pos, listname, index, stack, player)
  493. minetest.log("action", player:get_player_name() ..
  494. " moves stuff to protected chest at " ..
  495. minetest.pos_to_string(pos))
  496. end,
  497. on_metadata_inventory_take = function(pos, listname, index, stack, player)
  498. minetest.log("action", player:get_player_name() ..
  499. " takes stuff from protected chest at " ..
  500. minetest.pos_to_string(pos))
  501. end,
  502. on_metadata_inventory_move = function(
  503. pos, from_list, from_index, to_list, to_index, count, player)
  504. minetest.log("action", player:get_player_name() ..
  505. " moves stuff inside protected chest at " ..
  506. minetest.pos_to_string(pos))
  507. end,
  508. allow_metadata_inventory_put = function(pos, listname, index, stack, player)
  509. if minetest.is_protected(pos, player:get_player_name()) then
  510. return 0
  511. end
  512. return stack:get_count()
  513. end,
  514. allow_metadata_inventory_take = function(pos, listname, index, stack, player)
  515. if minetest.is_protected(pos, player:get_player_name()) then
  516. return 0
  517. end
  518. return stack:get_count()
  519. end,
  520. allow_metadata_inventory_move = function(
  521. pos, from_list, from_index, to_list, to_index, count, player)
  522. if minetest.is_protected(pos, player:get_player_name()) then
  523. return 0
  524. end
  525. return count
  526. end,
  527. on_rightclick = function(pos, node, clicker)
  528. if minetest.is_protected(pos, clicker:get_player_name()) then
  529. return
  530. end
  531. local meta = minetest.get_meta(pos)
  532. if not meta then
  533. return
  534. end
  535. local spos = pos.x .. "," .. pos.y .. "," ..pos.z
  536. local formspec
  537. -- mineclone support
  538. if mcl and mcf then
  539. formspec = "size[9,8.75]"
  540. .. "label[0,0;" .. minetest.formspec_escape(
  541. minetest.colorize("#313131", "Protected Chest")) .. "]"
  542. .. "list[nodemeta:" .. spos .. ";main;0,0.5;9,3;]"
  543. .. mcl_formspec.get_itemslot_bg(0,0.5,9,3)
  544. .. "image_button[3.0,3.5;1.05,0.8;protector_up_icon.png;protect_up;]"
  545. .. "image_button[4.0,3.5;1.05,0.8;protector_down_icon.png;protect_down;]"
  546. .. "label[0,4.0;" .. minetest.formspec_escape(
  547. minetest.colorize("#313131", "Inventory")) .. "]"
  548. .. "list[current_player;main;0,4.5;9,3;9]"
  549. .. mcl_formspec.get_itemslot_bg(0,4.5,9,3)
  550. .. "list[current_player;main;0,7.74;9,1;]"
  551. .. mcl_formspec.get_itemslot_bg(0,7.74,9,1)
  552. .. "listring[nodemeta:" .. spos .. ";main]"
  553. .. "listring[current_player;main]"
  554. else -- default formspec
  555. formspec = "size[8,9]"
  556. .. "list[nodemeta:".. spos .. ";main;0,0.3;8,4;]"
  557. .. "image_button[-0.01,4.26;1.05,0.8;protector_up_icon.png;protect_up;]"
  558. .. "image_button[0.98,4.26;1.05,0.8;protector_down_icon.png;protect_down;]"
  559. .. "tooltip[protect_up;" .. S("To Chest") .. "]"
  560. .. "tooltip[protect_down;" .. S("To Inventory") .. "]"
  561. .. "field[2.3,4.8;4,0.25;protect_name;;"
  562. .. meta:get_string("name") .. "]"
  563. .. "button[5.99,4.5;2.05,0.25;protect_rename;" .. S("Rename") .. "]"
  564. .. "list[current_player;main;0,5;8,1;]"
  565. .. "list[current_player;main;0,6.08;8,3;8]"
  566. .. "listring[nodemeta:" .. spos .. ";main]"
  567. .. "listring[current_player;main]"
  568. end
  569. minetest.show_formspec(clicker:get_player_name(),
  570. "protector:chest_" .. minetest.pos_to_string(pos), formspec)
  571. end,
  572. on_blast = function() end,
  573. })
  574. -- Container transfer helper
  575. local to_from = function(src, dst)
  576. local stack, item, leftover
  577. local size = dst:get_size("main")
  578. for i = 1, size do
  579. stack = src:get_stack("main", i)
  580. item = stack:get_name()
  581. if item ~= "" and dst:room_for_item("main", item) then
  582. leftover = dst:add_item("main", stack)
  583. if leftover and not leftover:is_empty() then
  584. src:set_stack("main", i, leftover)
  585. else
  586. src:set_stack("main", i, nil)
  587. end
  588. end
  589. end
  590. end
  591. -- Protected Chest formspec buttons
  592. minetest.register_on_player_receive_fields(function(player, formname, fields)
  593. if string.sub(formname, 0, 16) ~= "protector:chest_" then
  594. return
  595. end
  596. local pos_s = string.sub(formname, 17)
  597. local pos = minetest.string_to_pos(pos_s)
  598. if minetest.is_protected(pos, player:get_player_name()) then
  599. return
  600. end
  601. local meta = minetest.get_meta(pos) ; if not meta then return end
  602. local chest_inv = meta:get_inventory() ; if not chest_inv then return end
  603. local player_inv = player:get_inventory()
  604. -- copy contents of player inventory to chest
  605. if fields.protect_up then
  606. to_from(player_inv, chest_inv)
  607. -- copy contents of chest to player inventory
  608. elseif fields.protect_down then
  609. to_from(chest_inv, player_inv)
  610. elseif fields.protect_name or fields.protect_rename then
  611. -- change chest infotext to display name
  612. if fields.protect_name ~= "" then
  613. if fields.protect_name ~= string.match(fields.protect_name, "[%w%s_-]+")
  614. or fields.protect_name:len() > 35 then
  615. return
  616. end
  617. meta:set_string("name", fields.protect_name)
  618. meta:set_string("infotext", fields.protect_name)
  619. else
  620. meta:set_string("name", S("Protected Chest"))
  621. meta:set_string("infotext", S("Protected Chest"))
  622. end
  623. end
  624. end)
  625. -- Protected Chest recipes
  626. if protector_crafts then
  627. if mcl then
  628. minetest.register_craft({
  629. output = "protector:chest",
  630. recipe = {
  631. {"mcl_chests:chest", "mcl_core:gold_ingot"}
  632. }
  633. })
  634. else
  635. minetest.register_craft({
  636. output = "protector:chest",
  637. recipe = {
  638. {"group:wood", "group:wood", "group:wood"},
  639. {"group:wood", "default:copper_ingot", "group:wood"},
  640. {"group:wood", "group:wood", "group:wood"}
  641. }
  642. })
  643. minetest.register_craft({
  644. output = "protector:chest",
  645. recipe = {
  646. {"default:chest", "default:copper_ingot"}
  647. }
  648. })
  649. end
  650. end