Under certain circumstances, the ItemControl can cache an incorrect quantity. If you set the item to a stack from your vault or shared storage and then merge a stack from your backpack with a sufficient quantity to overflow the max stack size, the full stack will be a new item and the remainder will be put in the original stack. The QuantityChanged event will even correctly fire. However, the ItemControl will continue to display the stack as having the original quantity. A second issue arised from this since assigning the item to a new control will display the correct quantity but assigning the item to the original control will not refresh it, the control will continue to display the wrong quantity until you use SetItem to change the item the control contains and then set it back.
The obvious workaround for anyone encountering this is to use SetItem(nil) and then SetItem() in the QuantityChanged event handler to force the control to update the quantity it displays.
The detail below is for Turbine and is referenced in my bug report since it's easier to show here. Reproducing this is fairly easy once you understand the exact set of steps to create it. Here is a simple plugin that demonstrates the bug:
Code:
import "Turbine";
import "Turbine.Gameplay";
import "Turbine.UI";
import "Turbine.UI.Lotro";
localPlayer=Turbine.Gameplay.LocalPlayer:GetInstance()
vault=localPlayer:GetVault()
testWindow=Turbine.UI.Lotro.Window()
testWindow:SetSize(300,145)
testWindow:SetText("testing")
testWindow:SetVisible(true)
testControl1=Turbine.UI.Lotro.ItemControl()
testControl1:SetParent(testWindow)
testControl1:SetPosition(20,35)
testControl2=Turbine.UI.Lotro.ItemControl()
testControl2:SetParent(testWindow)
testControl2:SetPosition(245,35)
indexCaption=Turbine.UI.Label()
indexCaption:SetParent(testWindow)
indexCaption:SetSize(40,20)
indexCaption:SetPosition(108,45)
indexCaption:SetTextAlignment(Turbine.UI.ContentAlignment.MiddleCenter)
indexCaption:SetText("Index:")
testIndex=Turbine.UI.Lotro.TextBox()
testIndex:SetParent(testWindow)
testIndex:SetSize(40,20)
testIndex:SetPosition(152,45)
testIndex:SetFont(Turbine.UI.Lotro.Font.Verdana16)
testIndex:SetTextAlignment(Turbine.UI.ContentAlignment.MiddleLeft)
testIndex:SetText("1")
nameCaption=Turbine.UI.Label()
nameCaption:SetParent(testWindow)
nameCaption:SetSize(40,20)
nameCaption:SetPosition(10,75)
nameCaption:SetTextAlignment(Turbine.UI.ContentAlignment.MiddleCenter)
nameCaption:SetText("Name:")
findName=Turbine.UI.Lotro.TextBox()
findName:SetParent(testWindow)
findName:SetSize(170,20)
findName:SetPosition(55,75)
findName:SetFont(Turbine.UI.Lotro.Font.Verdana16)
findName:SetTextAlignment(Turbine.UI.ContentAlignment.MiddleLeft)
findName:SetText("")
findButton=Turbine.UI.Lotro.Button()
findButton:SetParent(testWindow)
findButton:SetSize(60,20)
findButton:SetPosition(230,75)
findButton:SetText("Find")
findButton.Click=function()
-- find the index of the next vault item matching the find text
if vault:IsAvailable() then
local count=vault:GetCount();
if count>0 then
local index=tonumber(testIndex:GetText());
if index==nil then index=1 end;
if index>count+1 then index=count+1 end;
local newIndex=index+1
local found=false
while newIndex~=index and not found do
if newIndex>count then
newIndex=1
end
Turbine.Shell.WriteLine("newIndex:"..tostring(newIndex).." "..vault:GetItem(newIndex):GetName())
if vault:GetItem(newIndex):GetName()==findName:GetText() then
found=true
else
if newIndex~=index then
newIndex=newIndex+1
end
end
end
if found then
testIndex:SetText(tostring(newIndex))
updateButton:Click()
end
end
end
end
updateButton=Turbine.UI.Lotro.Button()
updateButton:SetParent(testWindow)
updateButton:SetSize(100,20)
updateButton:SetPosition(100,100)
updateButton:SetText("update")
updateButton.Click=function()
if vault:IsAvailable() then
local index=tonumber(testIndex:GetText())
if index==nil or index<1 then index=1 end
if index>vault:GetCount() then index=vault:GetCount() end
testControl1:SetItem(vault:GetItem(index))
testControl2:SetItem(nil)
testControl2:SetItem(vault:GetItem(index))
end
end
To use the plugin, you will need two stacks of an item, both stacks less than a full stack (the bug isn't obvious when adding a full stack since the overflow is the same as the original quantity) but with enough to exceed the max stack size for the item. I used two stacks of "Large Hide", one with a quantity of 69 the other with a quantity of 50. Go to a vault-keeper, open your vault, sort by "Name A-Z" so that you can easily verify that you do not already have a stack of the item (move any of the item to your backpack before testing). Now add the first stack to your vault (I added the stack of 69 Large Hides). Load the plugin and type the name of a single item of the stack (in my case "Large Hide") and click "Find" - this will load both of the item controls in the plugin with the item from your vault (figure 1). Now add the second stack from your backpack to your vault (in my case 50 Large Hides). This will create an overflow and should create a new full stack and put the overflow in the original stack (in my case a stack of 19 Large Hides). At this point, the item controls should have updated to show the overflow quantity since the underlying item quantity changed but instead they will still display the original quantity (figure 2). The second issue and the work around can be observed by clicking the "Update" button. The control on the left is simply reassigned the same item and continues to display the wrong quantity (since the item being assigned is the same as the item already loaded, the control does not update) while the control on the right is first assigned a nil item and then reassigned the item and does update correctly (figure 3). If the quantity bug is fixed, then the second issue could be considered working as intended since the cached info would be updated so setting the same item would not need to update.

figure 1

figure 2

figure 3