• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

BuckarooBanzay / mapblock_lib / 11399363977

18 Oct 2024 07:24AM UTC coverage: 56.284% (-2.5%) from 58.802%
11399363977

push

github

BuckarooBanzay
generate preview image if the `isogen` mod is available

3 of 12 new or added lines in 1 file covered. (25.0%)

24 existing lines in 2 files now uncovered.

627 of 1114 relevant lines covered (56.28%)

2669.61 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

63.54
/serialize_mapblock.lua
1
---------
2
-- mapblock serialization
3

4
local air_content_id = minetest.get_content_id("air")
1✔
5
local ignore_content_id = minetest.get_content_id("ignore")
1✔
6
local placeholder_content_id = nil
1✔
7

8
local has_placeholder_mod = minetest.get_modpath("placeholder")
1✔
9
if has_placeholder_mod then
1✔
10
        placeholder_content_id = minetest.get_content_id("placeholder:placeholder")
2✔
11
end
12

13
-- collect node ids with on_timer attributes
14
local node_ids_with_timer = {}
1✔
15
minetest.register_on_mods_loaded(function()
2✔
16
        for _,node in pairs(minetest.registered_nodes) do
439✔
17
                if node.on_timer then
438✔
18
                        local nodeid = minetest.get_content_id(node.name)
54✔
19
                        node_ids_with_timer[nodeid] = true
54✔
20
                end
21
        end
22
end)
23

24
-- checks if a table is empty
25
local function is_empty(tbl)
UNCOV
26
        return not tbl or not next(tbl)
×
27
end
28

29
-- serialize the mapblock at the given mapblock-position
30
function mapblock_lib.serialize_mapblock(mapblock_pos)
2✔
31
        local manip = minetest.get_voxel_manip()
28✔
32
        local pos1, pos2 = mapblock_lib.get_mapblock_bounds_from_mapblock(mapblock_pos)
28✔
33
        local e1, e2 = manip:read_from_map(pos1, pos2)
28✔
34
        local area = VoxelArea:new({MinEdge=e1, MaxEdge=e2})
28✔
35

36
        local node_data = manip:get_data()
28✔
37
        local param1 = manip:get_light_data()
28✔
38
        local param2 = manip:get_param2_data()
28✔
39

40
        local node_id_map = {}
28✔
41

42
        -- id -> name
43
        local unknown_node_names = {}
28✔
44
        -- name -> id
45
        local unknown_node_ids = {}
28✔
46
        local next_unknown_nodeid = -1
28✔
47

48
        -- prepare data structure
49
        local data = {
28✔
50
                air_only = true,
51
                node_ids = {},
28✔
52
                node_mapping = {},
28✔
53
                param1 = {},
28✔
54
                param2 = {},
28✔
55
                metadata = nil
×
56
        }
57

58
        local timers = {}
28✔
59

60
        -- loop over all blocks and fill cid,param1 and param2
61
        for z=pos1.z,pos2.z do
476✔
62
                for y=pos1.y,pos2.y do
7,616✔
63
                        for x=pos1.x,pos2.x do
121,856✔
64
                                local i = area:index(x,y,z)
114,688✔
65
                                local pos = {x=x, y=y, z=z}
114,688✔
66

67
                                local node_id = node_data[i]
114,688✔
68
                                if node_id == ignore_content_id then
114,688✔
69
                                        -- replace ignore blocks with air
70
                                        node_id = air_content_id
×
71
                                end
72

73
                                if data.air_only and node_id ~= air_content_id then
114,688✔
74
                                        -- mapblock contains not jut air
75
                                        data.air_only = false
28✔
76
                                end
77

78
                                if node_ids_with_timer[node_id] then
114,688✔
79
                                        -- node has a node-timer
80
                                        local timer = minetest.get_node_timer(pos)
12,954✔
81
                                        local relative_pos = vector.subtract(pos, pos1)
12,954✔
82
                                        if timer:is_started() then
12,954✔
83
                                                timers[minetest.pos_to_string(relative_pos)] = {
4✔
84
                                                        timeout = timer:get_timeout(),
2✔
85
                                                        elapsed = math.floor(timer:get_elapsed()) -- truncate decimals
2✔
86
                                                }
2✔
87
                                        end
88
                                end
89

90
                                if has_placeholder_mod and node_id == placeholder_content_id then
114,688✔
91
                                        -- parse placeholder and set original node-data in serialized mapblock
92
                                        local meta = minetest.get_meta(pos)
×
93

94
                                        local original_node = placeholder.unwrap(meta)
×
95

96
                                        -- assign artifical node-id
97
                                        node_id = unknown_node_names[original_node.name]
×
98
                                        if not node_id then
×
99
                                                -- next unknown node-id
100
                                                node_id = next_unknown_nodeid
×
101
                                                next_unknown_nodeid = next_unknown_nodeid - 1
×
102
                                                unknown_node_names[original_node.name] = node_id
×
103
                                                unknown_node_ids[node_id] = original_node.name
×
104
                                        end
105
                                end
106

107
                                table.insert(data.node_ids, node_id)
114,688✔
108
                                table.insert(data.param1, param1[i])
114,688✔
109
                                if node_id == air_content_id then
114,688✔
110
                                        -- fixed param2
111
                                        table.insert(data.param2, 0)
45,547✔
112
                                else
113
                                        -- copy param2
114
                                        table.insert(data.param2, param2[i])
69,141✔
115
                                end
116

117
                                node_id_map[node_id] = true
114,688✔
118
                        end
119
                end
120
        end
121

122
        -- gather node id mapping
123
        for node_id in pairs(node_id_map) do
227✔
124
                local node_name = unknown_node_ids[node_id] or minetest.get_name_from_content_id(node_id)
199✔
125
                data.node_mapping[node_name] = node_id
199✔
126
        end
127

128
        if not data.air_only then
28✔
129
                -- serialize metadata
130
                local pos_with_meta = minetest.find_nodes_with_meta(pos1, pos2)
28✔
131
                for _, mpos in ipairs(pos_with_meta) do
28✔
UNCOV
132
                        local relative_pos = vector.subtract(mpos, pos1)
×
UNCOV
133
                        local i = area:indexp(mpos)
×
UNCOV
134
                        local node_id = node_data[i]
×
135

UNCOV
136
                        if has_placeholder_mod and node_id == placeholder_content_id then
×
137
                                -- placeholder
138
                                local meta = minetest.get_meta(mpos)
×
139
                                local _, metadata = placeholder.unwrap(meta)
×
140

141
                                if not is_empty(metadata.fields) or not is_empty(metadata.inventory) then
×
142
                                        data.metadata = data.metadata or {}
×
143
                                        data.metadata.meta = data.metadata.meta or {}
×
144
                                        data.metadata.meta[minetest.pos_to_string(relative_pos)] = metadata
×
145
                                end
146

UNCOV
147
                        elseif node_id ~= air_content_id then
×
148
                                -- only serialize metadata if the node isn't air
UNCOV
149
                                local meta = minetest.get_meta(mpos):to_table()
×
150

151
                                -- Convert metadata item stacks to item strings
UNCOV
152
                                for _, invlist in pairs(meta.inventory) do
×
UNCOV
153
                                        for index = 1, #invlist do
×
UNCOV
154
                                                local itemstack = invlist[index]
×
UNCOV
155
                                                if itemstack.to_string then
×
UNCOV
156
                                                        invlist[index] = itemstack:to_string()
×
157
                                                end
158
                                        end
159
                                end
160

161
                                -- re-check if metadata actually exists (may happen with minetest.find_nodes_with_meta)
UNCOV
162
                                if not is_empty(meta.fields) or not is_empty(meta.inventory) then
×
UNCOV
163
                                        data.metadata = data.metadata or {}
×
UNCOV
164
                                        data.metadata.meta = data.metadata.meta or {}
×
UNCOV
165
                                        data.metadata.meta[minetest.pos_to_string(relative_pos)] = meta
×
166
                                end
167

UNCOV
168
                                if not is_empty(timers) then
×
169
                                        data.metadata = data.metadata or {}
×
170
                                        data.metadata.timers = timers
×
171
                                end
172
                        end
173
                end
174
        end
175

176
        return data
28✔
177
end
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc