diff options
Diffstat (limited to 'worldedit')
-rw-r--r-- | worldedit/init.lua | 9 | ||||
-rw-r--r-- | worldedit/manipulations.lua | 23 | ||||
-rw-r--r-- | worldedit/primitives.lua | 88 |
3 files changed, 99 insertions, 21 deletions
diff --git a/worldedit/init.lua b/worldedit/init.lua index 0305c4d..8358e3b 100644 --- a/worldedit/init.lua +++ b/worldedit/init.lua @@ -1,6 +1,6 @@ --- Worldedit.
-- @module worldedit
--- @release 1.1
+-- @release 1.2
-- @copyright 2013 sfan5, Anthony Zhang (Uberi/Temperest), and Brett O'Donnell (cornernote).
-- @license GNU Affero General Public License version 3 (AGPLv3)
-- @author sfan5
@@ -8,9 +8,12 @@ -- @author Bret O'Donnel (cornernote)
-- @author ShadowNinja
+
worldedit = {}
-worldedit.version = {1, 1, major=1, minor=1}
-worldedit.version_string = table.concat(worldedit.version, ".")
+
+local ver = {major=1, minor=2}
+worldedit.version = ver
+worldedit.version_string = string.format("%d.%d", ver.major, ver.minor)
if not minetest.get_voxel_manip then
local err_msg = "This version of WorldEdit requires Minetest 0.4.8 or later! You have an old version."
diff --git a/worldedit/manipulations.lua b/worldedit/manipulations.lua index 57c7a76..995619c 100644 --- a/worldedit/manipulations.lua +++ b/worldedit/manipulations.lua @@ -38,6 +38,29 @@ function worldedit.set(pos1, pos2, node_names) return worldedit.volume(pos1, pos2)
end
+--- Sets param2 of a region.
+-- @param pos1
+-- @param pos2
+-- @param param2 Value of param2 to set
+-- @return The number of nodes set.
+function worldedit.set_param2(pos1, pos2, param2)
+ pos1, pos2 = worldedit.sort_pos(pos1, pos2)
+
+ local manip, area = mh.init(pos1, pos2)
+ local param2_data = manip:get_param2_data()
+
+ -- Set param2 for every node
+ for i in area:iterp(pos1, pos2) do
+ param2_data[i] = param2
+ end
+
+ -- Update map
+ manip:set_param2_data(param2_data)
+ manip:write_to_map()
+ manip:update_map()
+
+ return worldedit.volume(pos1, pos2)
+end
--- Replaces all instances of `search_node` with `replace_node` in a region.
-- When `inverse` is `true`, replaces all instances that are NOT `search_node`.
diff --git a/worldedit/primitives.lua b/worldedit/primitives.lua index fe22fff..1bebfde 100644 --- a/worldedit/primitives.lua +++ b/worldedit/primitives.lua @@ -4,6 +4,47 @@ local mh = worldedit.manip_helpers
+--- Adds a cube
+-- @param pos Position of ground level center of cube
+-- @param width Cube width. (x)
+-- @param height Cube height. (y)
+-- @param length Cube length. (z)
+-- @param node_name Name of node to make cube of.
+-- @param hollow Whether the cube should be hollow.
+-- @return The number of nodes added.
+function worldedit.cube(pos, width, height, length, node_name, hollow)
+ -- Set up voxel manipulator
+ local basepos = vector.subtract(pos, {x=math.floor(width/2), y=0, z=math.floor(length/2)})
+ local manip, area = mh.init(basepos, vector.add(basepos, {x=width, y=height, z=length}))
+ local data = mh.get_empty_data(area)
+
+ -- Add cube
+ local node_id = minetest.get_content_id(node_name)
+ local stride = {x=1, y=area.ystride, z=area.zstride}
+ local offset = vector.subtract(basepos, area.MinEdge)
+ local count = 0
+
+ for z = 0, length-1 do
+ local index_z = (offset.z + z) * stride.z + 1 -- +1 for 1-based indexing
+ for y = 0, height-1 do
+ local index_y = index_z + (offset.y + y) * stride.y
+ for x = 0, width-1 do
+ local is_wall = z == 0 or z == length-1
+ or y == 0 or y == height-1
+ or x == 0 or x == width-1
+ if not hollow or is_wall then
+ local i = index_y + (offset.x + x)
+ data[i] = node_id
+ count = count + 1
+ end
+ end
+ end
+ end
+
+ mh.finish(manip, data)
+ return count
+end
+
--- Adds a sphere of `node_name` centered at `pos`.
-- @param pos Position to center sphere at.
-- @param radius Sphere radius.
@@ -92,49 +133,60 @@ end -- @param pos Position to center base of cylinder at.
-- @param axis Axis ("x", "y", or "z")
-- @param length Cylinder length.
--- @param radius Cylinder radius.
+-- @param radius1 Cylinder base radius.
+-- @param radius2 Cylinder top radius.
-- @param node_name Name of node to make cylinder of.
-- @param hollow Whether the cylinder should be hollow.
-- @return The number of nodes added.
-function worldedit.cylinder(pos, axis, length, radius, node_name, hollow)
+function worldedit.cylinder(pos, axis, length, radius1, radius2, node_name, hollow)
local other1, other2 = worldedit.get_axis_others(axis)
+ -- Backwards compatibility
+ if type(radius2) == "string" then
+ hollow = node_name
+ node_name = radius2
+ radius2 = radius1 -- straight cylinder
+ end
+
-- Handle negative lengths
local current_pos = {x=pos.x, y=pos.y, z=pos.z}
if length < 0 then
length = -length
current_pos[axis] = current_pos[axis] - length
+ radius1, radius2 = radius2, radius1
end
-- Set up voxel manipulator
- local manip, area = mh.init_axis_radius_length(current_pos, axis, radius, length)
+ local manip, area = mh.init_axis_radius_length(current_pos, axis, math.max(radius1, radius2), length)
local data = mh.get_empty_data(area)
- -- Add cylinder
+ -- Add desired shape (anything inbetween cylinder & cone)
local node_id = minetest.get_content_id(node_name)
- local min_radius, max_radius = radius * (radius - 1), radius * (radius + 1)
local stride = {x=1, y=area.ystride, z=area.zstride}
local offset = {
x = current_pos.x - area.MinEdge.x,
y = current_pos.y - area.MinEdge.y,
z = current_pos.z - area.MinEdge.z,
}
- local min_slice, max_slice = offset[axis], offset[axis] + length - 1
local count = 0
- for index2 = -radius, radius do
- -- Offset contributed by other axis 1 plus 1 to make it 1-indexed
- local new_index2 = (index2 + offset[other1]) * stride[other1] + 1
- for index3 = -radius, radius do
- local new_index3 = new_index2 + (index3 + offset[other2]) * stride[other2]
- local squared = index2 * index2 + index3 * index3
- if squared <= max_radius and (not hollow or squared >= min_radius) then
- -- Position is in cylinder
- -- Add column along axis
- for index1 = min_slice, max_slice do
- local vi = new_index3 + index1 * stride[axis]
+ for i = 0, length - 1 do
+ -- Calulate radius for this "height" in the cylinder
+ local radius = radius1 + (radius2 - radius1) * (i + 1) / length
+ radius = math.floor(radius + 0.5) -- round
+ local min_radius, max_radius = radius * (radius - 1), radius * (radius + 1)
+
+ for index2 = -radius, radius do
+ -- Offset contributed by other axis 1 plus 1 to make it 1-indexed
+ local new_index2 = (index2 + offset[other1]) * stride[other1] + 1
+ for index3 = -radius, radius do
+ local new_index3 = new_index2 + (index3 + offset[other2]) * stride[other2]
+ local squared = index2 * index2 + index3 * index3
+ if squared <= max_radius and (not hollow or squared >= min_radius) then
+ -- Position is in cylinder, add node here
+ local vi = new_index3 + (offset[axis] + i) * stride[axis]
data[vi] = node_id
+ count = count + 1
end
- count = count + length
end
end
end
|