Fix metadata loss and. Improve placement for some corner cases.
This commit is contained in:
parent
b73bbd323e
commit
334f0a5065
|
@ -317,6 +317,8 @@ can be one of the source lists.
|
||||||
If destination list position is already occupied with some other item
|
If destination list position is already occupied with some other item
|
||||||
then function tries to move it to the source lists if possible.
|
then function tries to move it to the source lists if possible.
|
||||||
|
|
||||||
|
Warning!!! Moving oversized stacks is undefined and can lead to item loss!
|
||||||
|
|
||||||
Arguments:
|
Arguments:
|
||||||
inv: minetest inventory reference
|
inv: minetest inventory reference
|
||||||
src_lists: names of source lists
|
src_lists: names of source lists
|
||||||
|
@ -328,44 +330,48 @@ function unified_inventory.move_match(inv, src_lists, dst_list, match_table, amo
|
||||||
local moved_positions = {}
|
local moved_positions = {}
|
||||||
|
|
||||||
for item, pos_set in pairs(match_table) do
|
for item, pos_set in pairs(match_table) do
|
||||||
local stack_max = ItemStack(item):get_stack_max()
|
local needed = {}
|
||||||
|
local remained = {}
|
||||||
|
|
||||||
|
local stack = ItemStack(item)
|
||||||
|
local stack_max = stack:get_stack_max()
|
||||||
local bounded_amount = math.min(stack_max, amount)
|
local bounded_amount = math.min(stack_max, amount)
|
||||||
local pos_count = 0;
|
|
||||||
|
|
||||||
for _ in pairs(pos_set) do
|
-- Pass 1: Remove stacks needed for craft
|
||||||
pos_count = pos_count + 1
|
stack:set_count(bounded_amount)
|
||||||
end
|
|
||||||
|
|
||||||
local total = ItemStack{
|
|
||||||
name = item,
|
|
||||||
count = bounded_amount * pos_count
|
|
||||||
}
|
|
||||||
|
|
||||||
local removed = unified_inventory.remove_item(inv, src_lists, total)
|
|
||||||
local current = ItemStack(removed)
|
|
||||||
current:set_count(bounded_amount)
|
|
||||||
|
|
||||||
for pos in pairs(pos_set) do
|
for pos in pairs(pos_set) do
|
||||||
|
needed[pos] = unified_inventory.remove_item(inv, src_lists, stack)
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Pass 2: Remove remainder to free up positions
|
||||||
|
stack:set_count(stack_max)
|
||||||
|
|
||||||
|
for pos in pairs(pos_set) do
|
||||||
|
remained[pos] = unified_inventory.remove_item(inv, src_lists, stack)
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Pass 3: Move only needed stacks
|
||||||
|
for pos, current in pairs(needed) do
|
||||||
local occupied = inv:get_stack(dst_list, pos)
|
local occupied = inv:get_stack(dst_list, pos)
|
||||||
inv:set_stack(dst_list, pos, current)
|
inv:set_stack(dst_list, pos, current)
|
||||||
|
|
||||||
repeat
|
if not occupied:is_empty() then
|
||||||
if not occupied:is_empty() then
|
local leftover = unified_inventory.add_item(inv, src_lists, occupied)
|
||||||
local leftover = unified_inventory.add_item(inv, src_lists, occupied)
|
|
||||||
|
|
||||||
if not leftover:is_empty() then
|
if not leftover:is_empty() then
|
||||||
inv:set_stack(dst_list, pos, leftover)
|
inv:set_stack(dst_list, pos, leftover)
|
||||||
break
|
unified_inventory.add_item(inv, src_lists, current)
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
end
|
||||||
removed:take_item(bounded_amount)
|
|
||||||
until true
|
|
||||||
|
|
||||||
moved_positions[pos] = true
|
moved_positions[pos] = true
|
||||||
end
|
end
|
||||||
|
|
||||||
unified_inventory.add_item(inv, src_lists, removed)
|
-- Pass 4: Re-add remainder stacks
|
||||||
|
for _, current in pairs(remained) do
|
||||||
|
unified_inventory.add_item(inv, src_lists, current)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
unified_inventory.swap_items(inv, dst_list, src_lists, moved_positions)
|
unified_inventory.swap_items(inv, dst_list, src_lists, moved_positions)
|
||||||
|
|
Loading…
Reference in New Issue