Index: data/runes.lua ================================================================== --- data/runes.lua +++ data/runes.lua @@ -1160,10 +1160,11 @@ table.insert(ary, a) return true end return false end + local daytime = minetest.get_natural_light(ctr:offset(0,1,0)) > 9 for name,tree in pairs(sorcery.data.trees) do try(materials.corners, tree.node) try(materials.walls, tree.plank) try(materials.floor, tree.plank) end @@ -1198,15 +1199,15 @@ if math.random(1,10) == 7 then try(materials.corners, 'default:obsidianbrick') end try(materials.lamp_wall, 'default:torch_wall') - try(materials.lamp_wall, 'morelights_modern:wall_lamp') + try(materials.lamp_wall, 'morelights_modern:walllamp') - try(materials.lamp_ext, 'default:torch') - try(materials.lamp_ext, 'morelights_modern:wall_lamp') - try(materials.lamp_ext, 'morelights_modern:lantern_f') + try(materials.lamp_ext, 'default:torch_wall') + try(materials.lamp_ext, 'morelights_modern:walllamp') + try(materials.lamp_ext, 'morelights_vintage:lantern_w') for _, l in pairs { 'default:meselamp'; 'morelights_modern:barlight_s'; 'morelights_modern:ceilinglight'; @@ -1334,10 +1335,18 @@ end i=i+1 end local t_built = per*i local lighting = math.random(1,2) + local put_align = function(where,node,dir) + local dfn = function() return 0 end + local pt2 = minetest.registered_nodes[node].paramtype2 + if pt2 == 'facedir' or pt2 == 'wallmounted' then + dfn = minetest['dir_to_' .. pt2] + end + minetest.set_node(where, { name=node, param2=dfn(dir) }) + end if lighting == 1 then local lh = math.ceil(dim.y * .6) local wlamps = { ctr:offset( dim.rx - 1 , lh,0); ctr:offset(-(dim.rx - 1), lh,0); @@ -1349,14 +1358,11 @@ i = i + 10 timeline[{whence=0, secs = per*i}] = function(s) spark(s,where) local node = select(2,sorcery.lib.tbl.pick(materials.lamp_wall)) minetest.sound_play('sorcery_put',{pos=where,gain=0.8},true) - minetest.set_node(where, { - name=node; - param2=minetest.dir_to_wallmounted(vector.normalize(ctr:offset(0,lh,0) - where)*-1); - }) + put_align(where, node, vector.normalize(ctr:offset(0,lh,0) - where)*-1) end end i=i+1 elseif lighting == 2 then local which = math.random(1,3) if which == 1 or which == 2 then @@ -1390,24 +1396,23 @@ end i = i + 7 end end end - -- install door + + -- cut out door local doorside = ({ vector.new( dim.rx,1,0); vector.new(0,1, dim.rz); vector.new(-dim.rx,1,0); vector.new(0,1,-dim.rz); })[math.random(1,4)] + local doorslideaxis = doorside.z ~= 0 and 'x' or 'z' local doorpos if math.random(1,3) == 1 then - if doorside.z ~= 0 then - doorside.x = doorside.x + math.random(-(dim.rx-1), dim.rx-1) - elseif doorside.x ~= 0 then - doorside.z = doorside.z + math.random(-(dim.rz-1), dim.rz-1) - end + local d = dim['r'..doorslideaxis] - 1 + doorside[doorslideaxis] = doorside[doorslideaxis] + math.random(-d,d) end doorpos = ctr + doorside local door = mpick'door' i=i+5 timeline[{whence=0,secs=per*i}] = function(s) @@ -1422,10 +1427,50 @@ -- type = 'node'; -- above = doorpos; -- under = doorpos:offset(0,-1,0); -- }) end + + -- install outdoor lighting + if math.random(1,7) == 1 or not daytime then + local xwall,xspc = dim.rx, dim.rx+1 + local zwall,zspc = dim.rz, dim.rz+1 + local lh = dim.y - 1 + for _, o in pairs(sorcery.lib.node.offsets.corners) do + local w = ctr:add { + z = dim.rz * o.z; + x = dim.rx * o.x; + y = lh; + } + local put = function(ofs) + timeline[{whence=0,secs=per*i}] = function(s) + local p = vector.add(w,ofs) + if not sorcery.lib.node.is_clear(p) then return end + spark(s, p) + minetest.sound_play('sorcery_put', {pos = p, gain = 0.4}, true) + local lamp = mpick 'lamp_ext' + print('installing lamp',lamp,p,vector.new(ofs)) + put_align(p, lamp, vector.multiply(ofs,-1)) + end + i=i+1 + end + put{x=o.x, y=0, z=0} + put{x=0, y=0, z=o.z} + end + end + + -- lay down bed + i=i+3 + timeline[{whence=0,secs=per*i}] = function(s) + local bed = 'beds:bed' + if math.random(1,3) == 1 then bed = 'beds:fancy_bed' end + local top = ctr:offset(dim.rx-1,1,dim.rz-1) + sorcery.lib.node.install_bed(bed, top, vector.new(1,0,0)) + spark(s, top) + spark(s, top:offset(-1,0,0)) + minetest.sound_play('sorcery_put', {pos = doorpos, gain = 0.9}, true) + end sorcery.spell.cast { name = 'sorcery:shelter'; groups = {'genesis','construct'}; caster = ctx.caster; Index: lib/node.lua ================================================================== --- lib/node.lua +++ lib/node.lua @@ -6,10 +6,16 @@ {x = 1, y = 0, z = 0}; {x = -1, y = 0, z = 0}; {x = 0, y = 0, z = 1}; {x = 0, y = 0, z = -1}; }; + corners = { + {x = 1, y = 0, z = 1}; + {x = -1, y = 0, z = 1}; + {x = -1, y = 0, z = -1}; + {x = 1, y = 0, z = -1}; + }; planecorners = { {x = 1, y = 0, z = 1}; {x = -1, y = 0, z = 1}; {x = -1, y = 0, z = -1}; {x = 1, y = 0, z = -1}; @@ -115,33 +121,35 @@ i = i + 1 until i > #stack return nodes, positions end; +local is_air = function(pos) + local n = force(pos) + if n.name == 'air' then return true end + local d = minetest.registered_nodes[n.name] + if not d then return false end + return (d.walkable == false) and (d.drawtype == 'airlike' or d.buildable_to == true) +end; + +local is_clear = function(pos) + if not sorcery.lib.node.is_air(pos) then return false end + local ents = minetest.get_objects_inside_radius(pos,0.5) + if #ents > 0 then return false end + return true +end; return { offsets = ofs; purge_container = function(...) return purge_container(nil, ...) end; purge_only = function(lst) return function(...) return purge_container(lst, ...) end end; - is_air = function(pos) - local n = force(pos) - if n.name == 'air' then return true end - local d = minetest.registered_nodes[n.name] - if not d then return false end - return (d.walkable == false) and (d.drawtype == 'airlike' or d.buildable_to == true) - end; - - is_clear = function(pos) - if not sorcery.lib.node.is_air(pos) then return false end - local ents = minetest.get_objects_inside_radius(pos,0.5) - if #ents > 0 then return false end - return true - end; + is_air = is_air; + is_clear = is_clear; insert = function(item, slot, npos, user, inv) inv = inv or minetest.get_meta(npos):get_inventory() if inv:room_for_item(slot,item) then inv:add_item(slot,item) @@ -154,10 +162,26 @@ end end minetest.add_item(npos, item) until true end end; + + install_bed = function(bed, where, dir) + local bottom = bed .. '_bottom' + local top = bed .. '_top' + local d + if type(dir) == 'number' then + d = dir + dir = minetest.facedir_to_dir(d) + else + d = minetest.dir_to_facedir(dir) + end + if not is_clear(where) and is_clear(where - dir) then return false end + minetest.set_node(where, {name = top, param2 = d}) + minetest.set_node(where - dir, {name = bottom, param2 = d}) + return true + end; tree_is_live = function(pos, checklight) -- VERY EXPENSIVE FUNCTION -- this is going to require some explanation. -- -- for various purposes, we want to be able to tell the difference between @@ -213,11 +237,12 @@ -- meta keys for me to consider it an option. -- -- verdict: not very good, but decent enough for most cases. mtg should have -- done better than this, but now we're all stuck with their bullshit -- - -- UPDATE: in pratice this is way too expensive to be functional, and causes servers to hang. we're replacing it with a simpler version + -- UPDATE: in practice this was way too expensive to be functional, and causes + -- servers to hang. ripped it out and replaced it with a simpler version local treetype = force(pos).name if minetest.get_item_group(treetype, 'tree') == 0 then -- sir this is not a tree return nil -- 無 end Index: recipes.lua ================================================================== --- recipes.lua +++ recipes.lua @@ -489,11 +489,11 @@ },1,{ {'basic_materials:silver_wire', 'basic_materials:empty_spool'}; {'basic_materials:silver_wire', 'basic_materials:empty_spool'}; {'basic_materials:silver_wire', 'basic_materials:empty_spool'}; }) - +regtech('axial_dispulsor', 'Axial Dispulsor',{metal=1}) regtech('conduction_plate', 'Conduction Plate', {metal = 1}, { {'','sorcery:disc_copper',''}; {'','stairs:slab_stone',''}; {'basic_materials:copper_wire','basic_materials:steel_bar','basic_materials:copper_wire'}; }, 1, {