feat: imbuement system (#1616)
New Features: - Imbuement Shrine UI: item/scroll selection, imbuement/clear flows, confirmation dialogs, timers, and cost display. - New imbuement modules: selection, item/scroll handlers, and imbuement management. - New progress bar widgets and vertical/inverted variants for status and timers. - Exposed client APIs and protocol support for imbuement interactions. UX Improvements: - Resource requirement tooltips, formatted balance display, and conditional enablement of imbue actions. Co-authored-by: kokekanon <114332266+kokekanon@users.noreply.github.com>
|
Before Width: | Height: | Size: 1.5 KiB After Width: | Height: | Size: 2.3 KiB |
BIN
data/images/game/prey/balanceBg.png
Normal file
|
After Width: | Height: | Size: 1.9 KiB |
BIN
data/images/ui/infoPanel.png
Normal file
|
After Width: | Height: | Size: 1.9 KiB |
BIN
data/images/ui/item66.png
Normal file
|
After Width: | Height: | Size: 3.2 KiB |
BIN
data/images/ui/right-arrow.png
Normal file
|
After Width: | Height: | Size: 831 B |
BIN
data/images/ui/t2pixel-up-frame-borderimage_2.png
Normal file
|
After Width: | Height: | Size: 33 KiB |
|
|
@ -57,4 +57,4 @@ InvVerticalBar < UIVerticalProgressBarSDInverted
|
|||
|
||||
VerticalBar < UIVerticalProgressBarSD
|
||||
size: 10 30
|
||||
image-border: 1
|
||||
image-border: 1
|
||||
|
|
|
|||
|
|
@ -5,8 +5,8 @@ function UIProgressBarSD.create()
|
|||
local progressbar = UIProgressBarSD.internalCreate()
|
||||
progressbar:setFocusable(false)
|
||||
progressbar:setOn(true)
|
||||
progressbar.min = 0
|
||||
progressbar.max = 100
|
||||
progressbar.minimum = 0
|
||||
progressbar.maximum = 100
|
||||
progressbar.value = 0
|
||||
progressbar.bgBorderLeft = 0
|
||||
progressbar.bgBorderRight = 0
|
||||
|
|
|
|||
|
|
@ -5,8 +5,8 @@ function UIProgressBarSDInverted.create()
|
|||
local progressbar = UIProgressBarSDInverted.internalCreate()
|
||||
progressbar:setFocusable(false)
|
||||
progressbar:setOn(true)
|
||||
progressbar.min = 0
|
||||
progressbar.max = 100
|
||||
progressbar.minimum = 0
|
||||
progressbar.maximum = 100
|
||||
progressbar.value = 0
|
||||
progressbar.bgBorderLeft = 0
|
||||
progressbar.bgBorderRight = 0
|
||||
|
|
|
|||
BIN
modules/game_imbuing/images/clear.png
Normal file
|
After Width: | Height: | Size: 5.4 KiB |
BIN
modules/game_imbuing/images/imbue_empty.png
Normal file
|
After Width: | Height: | Size: 4.2 KiB |
BIN
modules/game_imbuing/images/imbue_green.png
Normal file
|
After Width: | Height: | Size: 5.4 KiB |
BIN
modules/game_imbuing/images/imbui-progress.png
Normal file
|
After Width: | Height: | Size: 252 B |
BIN
modules/game_imbuing/images/imbui-timer-bg.png
Normal file
|
After Width: | Height: | Size: 3.9 KiB |
|
|
@ -1,349 +1,158 @@
|
|||
Imbuing = {}
|
||||
local imbuingWindow
|
||||
local bankGold = 0
|
||||
local inventoryGold = 0
|
||||
local itemImbuements = {}
|
||||
local emptyImbue
|
||||
local groupsCombo
|
||||
local imbueLevelsCombo
|
||||
local protectionBtn
|
||||
local clearImbue
|
||||
local selectedImbue
|
||||
local imbueItems = {}
|
||||
local protection = false
|
||||
local clearConfirmWindow
|
||||
local imbueConfirmWindow
|
||||
local MODERN_IMBUEMENT_VERSION = 1510
|
||||
|
||||
function init()
|
||||
connect(g_game, {
|
||||
onGameEnd = hide,
|
||||
onResourcesBalanceChange = Imbuing.onResourcesBalanceChange,
|
||||
onImbuementWindow = Imbuing.onImbuementWindow,
|
||||
onCloseImbuementWindow = Imbuing.onCloseImbuementWindow
|
||||
})
|
||||
local activeDesign
|
||||
local activeDesignName
|
||||
|
||||
imbuingWindow = g_ui.displayUI('imbuing')
|
||||
emptyImbue = imbuingWindow.emptyImbue
|
||||
groupsCombo = emptyImbue.groups
|
||||
imbueLevelsCombo = emptyImbue.imbuement
|
||||
protectionBtn = emptyImbue.protection
|
||||
clearImbue = imbuingWindow.clearImbue
|
||||
imbuingWindow:hide()
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
bankGold = player:getResourceBalance(ResourceTypes.BANK_BALANCE)
|
||||
inventoryGold = player:getResourceBalance(ResourceTypes.GOLD_EQUIPPED)
|
||||
imbuingWindow.balance:setText(tr('Balance') .. ':\n' .. (player:getTotalMoney()))
|
||||
local function isModernImbuementWindow()
|
||||
return g_game.getClientVersion() >= MODERN_IMBUEMENT_VERSION
|
||||
end
|
||||
|
||||
local function terminateActiveDesign()
|
||||
if activeDesign and activeDesign.terminate then
|
||||
activeDesign.terminate()
|
||||
end
|
||||
|
||||
groupsCombo.onOptionChange = function(widget)
|
||||
imbueLevelsCombo:clearOptions()
|
||||
if itemImbuements ~= nil then
|
||||
local selectedGroup = groupsCombo:getCurrentOption().text
|
||||
for _, imbuement in ipairs(itemImbuements) do
|
||||
if imbuement['group'] == selectedGroup then
|
||||
emptyImbue.imbuement:addOption(imbuement['name'])
|
||||
end
|
||||
end
|
||||
imbueLevelsCombo.onOptionChange(imbueLevelsCombo) -- update options
|
||||
end
|
||||
activeDesign = nil
|
||||
activeDesignName = nil
|
||||
end
|
||||
|
||||
local function activateDesign(name)
|
||||
if activeDesignName == name and activeDesign then
|
||||
return activeDesign
|
||||
end
|
||||
|
||||
imbueLevelsCombo.onOptionChange = function(widget)
|
||||
setProtection(false)
|
||||
local selectedGroup = groupsCombo:getCurrentOption().text
|
||||
for _, imbuement in ipairs(itemImbuements) do
|
||||
if imbuement['group'] == selectedGroup then
|
||||
if #imbuement['sources'] == widget.currentIndex then
|
||||
selectedImbue = imbuement
|
||||
for i, source in ipairs(imbuement['sources']) do
|
||||
for _, item in ipairs(imbueItems) do
|
||||
if item:getId() == source['item']:getId() then
|
||||
if item:getCount() >= source['item']:getCount() then
|
||||
emptyImbue.imbue:setImageSource('/images/game/imbuing/imbue_green')
|
||||
emptyImbue.imbue:setEnabled(true)
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setColor('white')
|
||||
end
|
||||
if item:getCount() < source['item']:getCount() then
|
||||
emptyImbue.imbue:setEnabled(false)
|
||||
emptyImbue.imbue:setImageSource('/images/game/imbuing/imbue_empty')
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setColor('red')
|
||||
end
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setText(item:getCount() .. '/' ..
|
||||
source['item']:getCount())
|
||||
end
|
||||
end
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setItemId(source['item']:getId())
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setTooltip('The imbuement requires ' ..
|
||||
source['description'] .. '.')
|
||||
end
|
||||
for i = 3, widget.currentIndex + 1, -1 do
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setText('')
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setItemId(0)
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setTooltip('')
|
||||
end
|
||||
emptyImbue.protectionCost:setText(imbuement['protectionCost'])
|
||||
emptyImbue.cost:setText(imbuement['cost'])
|
||||
if not protection and (bankGold + inventoryGold) < imbuement['cost'] then
|
||||
emptyImbue.imbue:setEnabled(false)
|
||||
emptyImbue.imbue:setImageSource('/images/game/imbuing/imbue_empty')
|
||||
emptyImbue.cost:setColor('red')
|
||||
end
|
||||
if not protection and (bankGold + inventoryGold) >= imbuement['cost'] then
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
if protection and (bankGold + inventoryGold) < (imbuement['cost'] + imbuement['protectionCost']) then
|
||||
emptyImbue.imbue:setEnabled(false)
|
||||
emptyImbue.imbue:setImageSource('/images/game/imbuing/imbue_empty')
|
||||
emptyImbue.cost:setColor('red')
|
||||
end
|
||||
if protection and (bankGold + inventoryGold) >= (imbuement['cost'] + imbuement['protectionCost']) then
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
emptyImbue.successRate:setText(imbuement['successRate'] .. '%')
|
||||
if selectedImbue['successRate'] > 50 then
|
||||
emptyImbue.successRate:setColor('white')
|
||||
else
|
||||
emptyImbue.successRate:setColor('red')
|
||||
end
|
||||
emptyImbue.description:setText(imbuement['description'])
|
||||
end
|
||||
end
|
||||
end
|
||||
terminateActiveDesign()
|
||||
|
||||
if name == 'new' then
|
||||
activeDesign = dofile('new_design/main')
|
||||
elseif name == 'old' then
|
||||
activeDesign = dofile('old_design/imbuing')
|
||||
else
|
||||
error('Unknown imbuing design: ' .. tostring(name))
|
||||
end
|
||||
|
||||
protectionBtn.onClick = function()
|
||||
setProtection(not protection)
|
||||
if type(activeDesign) ~= 'table' then
|
||||
error('Imbuing design "' .. tostring(name) .. '" did not return a valid API table')
|
||||
end
|
||||
|
||||
activeDesignName = name
|
||||
if activeDesign.init then
|
||||
activeDesign.init()
|
||||
end
|
||||
|
||||
return activeDesign
|
||||
end
|
||||
|
||||
local function callActive(method, ...)
|
||||
if activeDesign and activeDesign[method] then
|
||||
return activeDesign[method](...)
|
||||
end
|
||||
end
|
||||
|
||||
function setProtection(value)
|
||||
protection = value
|
||||
if protection then
|
||||
emptyImbue.cost:setText(selectedImbue['cost'] + selectedImbue['protectionCost'])
|
||||
emptyImbue.successRate:setText('100%')
|
||||
emptyImbue.successRate:setColor('green')
|
||||
protectionBtn:setImageClip(torect('66 0 66 66'))
|
||||
local function callNew(method, ...)
|
||||
return activateDesign('new')[method](...)
|
||||
end
|
||||
|
||||
local function callOld(method, ...)
|
||||
return activateDesign('old')[method](...)
|
||||
end
|
||||
|
||||
local function onGameStart()
|
||||
terminateActiveDesign()
|
||||
end
|
||||
|
||||
local function onGameEnd()
|
||||
terminateActiveDesign()
|
||||
end
|
||||
|
||||
local function onOpenImbuementWindow(...)
|
||||
return callNew('onOpenImbuementWindow', ...)
|
||||
end
|
||||
|
||||
local function onImbuementItem(...)
|
||||
if isModernImbuementWindow() then
|
||||
return callNew('onImbuementItem', ...)
|
||||
else
|
||||
if selectedImbue then
|
||||
emptyImbue.cost:setText(selectedImbue['cost'])
|
||||
emptyImbue.successRate:setText(selectedImbue['successRate'] .. '%')
|
||||
if selectedImbue['successRate'] > 50 then
|
||||
emptyImbue.successRate:setColor('white')
|
||||
else
|
||||
emptyImbue.successRate:setColor('red')
|
||||
end
|
||||
end
|
||||
protectionBtn:setImageClip(torect('0 0 66 66'))
|
||||
return callOld('onImbuementItem', ...)
|
||||
end
|
||||
end
|
||||
|
||||
local function onImbuementScroll(...)
|
||||
return callNew('onImbuementScroll', ...)
|
||||
end
|
||||
|
||||
local function onResourcesBalanceChange(...)
|
||||
if activeDesignName == 'old' and not isModernImbuementWindow() then
|
||||
return callActive('onResourcesBalanceChange', ...)
|
||||
end
|
||||
end
|
||||
|
||||
local function onCloseImbuementWindow()
|
||||
terminateActiveDesign()
|
||||
end
|
||||
|
||||
local function onMessageDialog(...)
|
||||
if activeDesignName == 'new' then
|
||||
return callActive('onMessageDialog', ...)
|
||||
end
|
||||
end
|
||||
|
||||
function hide()
|
||||
return callActive('hide')
|
||||
end
|
||||
|
||||
function close()
|
||||
return callActive('close')
|
||||
end
|
||||
|
||||
function onSelectItem()
|
||||
return callActive('onSelectItem')
|
||||
end
|
||||
|
||||
function onSelectScroll()
|
||||
return callActive('onSelectScroll')
|
||||
end
|
||||
|
||||
function onItemSlot(widget)
|
||||
return callActive('onItemSlot', widget)
|
||||
end
|
||||
|
||||
function onItemBaseType(selectedButtonId)
|
||||
return callActive('onItemBaseType', selectedButtonId)
|
||||
end
|
||||
|
||||
function onScrollBaseType(selectedButtonId)
|
||||
return callActive('onScrollBaseType', selectedButtonId)
|
||||
end
|
||||
|
||||
function init()
|
||||
connect(g_game, {
|
||||
onGameStart = onGameStart,
|
||||
onGameEnd = onGameEnd,
|
||||
onOpenImbuementWindow = onOpenImbuementWindow,
|
||||
onImbuementItem = onImbuementItem,
|
||||
onImbuementScroll = onImbuementScroll,
|
||||
onResourcesBalanceChange = onResourcesBalanceChange,
|
||||
onCloseImbuementWindow = onCloseImbuementWindow,
|
||||
onMessageDialog = onMessageDialog
|
||||
})
|
||||
|
||||
if g_game.isOnline() then
|
||||
addEvent(onGameStart)
|
||||
end
|
||||
end
|
||||
|
||||
function terminate()
|
||||
disconnect(g_game, {
|
||||
onGameEnd = hide,
|
||||
onResourcesBalanceChange = Imbuing.onResourcesBalanceChange,
|
||||
onImbuementWindow = Imbuing.onImbuementWindow,
|
||||
onCloseImbuementWindow = Imbuing.onCloseImbuementWindow
|
||||
onGameStart = onGameStart,
|
||||
onGameEnd = onGameEnd,
|
||||
onOpenImbuementWindow = onOpenImbuementWindow,
|
||||
onImbuementItem = onImbuementItem,
|
||||
onImbuementScroll = onImbuementScroll,
|
||||
onResourcesBalanceChange = onResourcesBalanceChange,
|
||||
onCloseImbuementWindow = onCloseImbuementWindow,
|
||||
onMessageDialog = onMessageDialog
|
||||
})
|
||||
|
||||
imbuingWindow:destroy()
|
||||
end
|
||||
|
||||
function resetSlots()
|
||||
emptyImbue:setVisible(false)
|
||||
clearImbue:setVisible(false)
|
||||
for i = 1, 3 do
|
||||
imbuingWindow.itemInfo.slots:getChildByIndex(i):setText('Slot ' .. i)
|
||||
imbuingWindow.itemInfo.slots:getChildByIndex(i):setEnabled(false)
|
||||
imbuingWindow.itemInfo.slots:getChildByIndex(i):setTooltip(
|
||||
'Items can have up to three imbuements slots. This slot is not available for this item.')
|
||||
imbuingWindow.itemInfo.slots:getChildByIndex(i).onClick = nil
|
||||
end
|
||||
end
|
||||
|
||||
function selectSlot(widget, slotId, activeSlot)
|
||||
if activeSlot then
|
||||
emptyImbue:setVisible(false)
|
||||
widget:setText(activeSlot[1]['name'])
|
||||
clearImbue.title:setText('Clear Imbuement "' .. activeSlot[1]['name'] .. '"')
|
||||
clearImbue.groups:clearOptions()
|
||||
clearImbue.groups:addOption(activeSlot[1]['group'])
|
||||
clearImbue.imbuement:clearOptions()
|
||||
clearImbue.imbuement:addOption(activeSlot[1]['name'])
|
||||
clearImbue.description:setText(activeSlot[1]['description'])
|
||||
|
||||
hours = string.format('%02.f', math.floor(activeSlot[2] / 3600))
|
||||
mins = string.format('%02.f', math.floor(activeSlot[2] / 60 - (hours * 60)))
|
||||
clearImbue.time.timeRemaining:setText(hours .. ':' .. mins .. 'h')
|
||||
|
||||
clearImbue.cost:setText(activeSlot[3])
|
||||
if (bankGold + inventoryGold) < activeSlot[3] then
|
||||
emptyImbue.clear:setEnabled(false)
|
||||
emptyImbue.clear:setImageSource('/images/game/imbuing/imbue_empty')
|
||||
emptyImbue.cost:setColor('red')
|
||||
end
|
||||
|
||||
local yesCallback = function()
|
||||
g_game.clearImbuement(slotId)
|
||||
widget:setText('Slot ' .. (slotId + 1))
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
end
|
||||
local noCallback = function()
|
||||
imbuingWindow:show()
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
clearImbue.clear.onClick = function()
|
||||
imbuingWindow:hide()
|
||||
clearConfirmWindow = displayGeneralBox(tr('Confirm Clearing'),
|
||||
tr(
|
||||
'Do you wish to spend ' .. activeSlot[3] ..
|
||||
' gold coins to clear the imbuement "' ..
|
||||
activeSlot[1]['name'] .. '" from your item?'), {
|
||||
{
|
||||
text = tr('Yes'),
|
||||
callback = yesCallback
|
||||
},
|
||||
{
|
||||
text = tr('No'),
|
||||
callback = noCallback
|
||||
},
|
||||
anchor = AnchorHorizontalCenter
|
||||
}, yesCallback, noCallback)
|
||||
end
|
||||
|
||||
clearImbue:setVisible(true)
|
||||
else
|
||||
emptyImbue:setVisible(true)
|
||||
clearImbue:setVisible(false)
|
||||
|
||||
local yesCallback = function()
|
||||
g_game.applyImbuement(slotId, selectedImbue['id'], protection)
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
widget:setText(selectedImbue['name'])
|
||||
imbuingWindow:show()
|
||||
end
|
||||
local noCallback = function()
|
||||
imbuingWindow:show()
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
emptyImbue.imbue.onClick = function()
|
||||
imbuingWindow:hide()
|
||||
local cost = selectedImbue['cost']
|
||||
local successRate = selectedImbue['successRate']
|
||||
if protection then
|
||||
cost = cost + selectedImbue['protectionCost']
|
||||
successRate = '100'
|
||||
end
|
||||
clearConfirmWindow = displayGeneralBox(tr('Confirm Imbuing Attempt'),
|
||||
'You are about to imbue your item with "' .. selectedImbue['name'] ..
|
||||
'".\nYour chance to succeed is ' .. successRate ..
|
||||
'%. It will consume the required astral sources and ' .. cost ..
|
||||
' gold coins.\nDo you wish to proceed?', {
|
||||
{
|
||||
text = tr('Yes'),
|
||||
callback = yesCallback
|
||||
},
|
||||
{
|
||||
text = tr('No'),
|
||||
callback = noCallback
|
||||
},
|
||||
anchor = AnchorHorizontalCenter
|
||||
}, yesCallback, noCallback)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function Imbuing.onImbuementWindow(itemId, slots, activeSlots, imbuements, needItems)
|
||||
if not itemId then
|
||||
return
|
||||
end
|
||||
resetSlots()
|
||||
imbueItems = table.copy(needItems)
|
||||
imbuingWindow.itemInfo.item:setItemId(itemId)
|
||||
|
||||
for i = 1, slots do
|
||||
local slot = imbuingWindow.itemInfo.slots:getChildByIndex(i)
|
||||
slot.onClick = function(widget)
|
||||
selectSlot(widget, i - 1)
|
||||
end
|
||||
slot:setTooltip(
|
||||
'Use this slot to imbue your item. Depending on the item you can have up to three different imbuements.')
|
||||
slot:setEnabled(true)
|
||||
|
||||
if slot:getId() == 'slot0' then
|
||||
selectSlot(slot, i - 1)
|
||||
end
|
||||
end
|
||||
|
||||
for i, slot in pairs(activeSlots) do
|
||||
local activeSlotBtn = imbuingWindow.itemInfo.slots:getChildById('slot' .. i)
|
||||
activeSlotBtn.onClick = function(widget)
|
||||
selectSlot(widget, i, slot)
|
||||
end
|
||||
if activeSlotBtn:getId() == 'slot0' then
|
||||
selectSlot(activeSlotBtn, i, slot)
|
||||
end
|
||||
end
|
||||
|
||||
if imbuements ~= nil then
|
||||
groupsCombo:clearOptions()
|
||||
imbueLevelsCombo:clearOptions()
|
||||
itemImbuements = table.copy(imbuements)
|
||||
for _, imbuement in ipairs(itemImbuements) do
|
||||
if not groupsCombo:isOption(imbuement['group']) then
|
||||
groupsCombo:addOption(imbuement['group'])
|
||||
end
|
||||
end
|
||||
end
|
||||
show()
|
||||
end
|
||||
|
||||
function Imbuing.onResourcesBalanceChange(balance, oldBalance, type)
|
||||
if type == ResourceTypes.BANK_BALANCE then
|
||||
bankGold = balance
|
||||
elseif type == ResourceTypes.GOLD_EQUIPPED then
|
||||
inventoryGold = balance
|
||||
end
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
if type == ResourceTypes.BANK_BALANCE or type == ResourceTypes.GOLD_EQUIPPED then
|
||||
imbuingWindow.balance:setText(tr('Balance') .. ':\n' .. (player:getTotalMoney()))
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function Imbuing.onCloseImbuementWindow()
|
||||
resetSlots()
|
||||
end
|
||||
|
||||
function hide()
|
||||
g_game.closeImbuingWindow()
|
||||
imbuingWindow:hide()
|
||||
end
|
||||
|
||||
function show()
|
||||
imbuingWindow:show()
|
||||
imbuingWindow:raise()
|
||||
imbuingWindow:focus()
|
||||
end
|
||||
|
||||
function toggle()
|
||||
if imbuingWindow:isVisible() then
|
||||
return hide()
|
||||
end
|
||||
show()
|
||||
terminateActiveDesign()
|
||||
end
|
||||
|
|
|
|||
|
|
@ -6,4 +6,4 @@ Module
|
|||
sandboxed: true
|
||||
scripts: [ imbuing ]
|
||||
@onLoad: init()
|
||||
@onUnload: terminate()
|
||||
@onUnload: terminate()
|
||||
|
|
|
|||
442
modules/game_imbuing/new_design/classes/imbuementitem.lua
Normal file
|
|
@ -0,0 +1,442 @@
|
|||
return function(context)
|
||||
local itemApi = {
|
||||
window = nil,
|
||||
confirmWindow = nil,
|
||||
lastselectedwidget = nil,
|
||||
selectedSlot = 0,
|
||||
itemId = 0,
|
||||
tier = 0,
|
||||
slots = 0,
|
||||
activeSlots = {},
|
||||
availableImbuements = {},
|
||||
needItems = {},
|
||||
}
|
||||
|
||||
itemApi.__index = itemApi
|
||||
|
||||
local self = itemApi
|
||||
function itemApi.setup(itemId, tier, slots, activeSlots, availableImbuements, needItems)
|
||||
self.itemId = itemId
|
||||
self.tier = tier
|
||||
self.slots = slots
|
||||
|
||||
self.activeSlots = {}
|
||||
for i = 0, slots - 1 do
|
||||
self.activeSlots["slot"..i] = activeSlots[i] or {}
|
||||
end
|
||||
self.availableImbuements = availableImbuements or {}
|
||||
self.needItems = needItems or {}
|
||||
|
||||
for i = 0, 2 do
|
||||
context.imbuement.clearImbue:recursiveGetChildById("slot"..i):setBorderWidth(0)
|
||||
context.imbuement.selectImbue:recursiveGetChildById("slot"..i):setBorderWidth(0)
|
||||
end
|
||||
|
||||
self.selectedSlot = 0
|
||||
self.onSelectImbuementSlot(self.selectedSlot)
|
||||
|
||||
-- Verificar se o slot 0 tem um imbuement ativo e passar para updateWindowState
|
||||
local imbuement = self.activeSlots["slot0"]
|
||||
self.updateWindowState(imbuement)
|
||||
|
||||
self.configureWindow(context.imbuement.selectImbue)
|
||||
self.configureWindow(context.imbuement.clearImbue)
|
||||
end
|
||||
|
||||
function itemApi.configureWindow(window)
|
||||
local slots = window:recursiveGetChildById("slots")
|
||||
for i = 1, 3 do
|
||||
local slotWidget = slots:getChildById("slot"..i - 1)
|
||||
if slotWidget then
|
||||
slotWidget.resource:setImageSource("//images/game/imbuing/icons//0")
|
||||
if i <= self.slots then
|
||||
slotWidget:setVisible(true)
|
||||
local imbuement = self.activeSlots["slot"..i - 1]
|
||||
if imbuement and imbuement[1] then
|
||||
if imbuement[1].id and imbuement[1].id ~= 0 then
|
||||
slotWidget.resource:setImageSource("//images/game/imbuing/icons//" .. imbuement[1]["imageId"])
|
||||
end
|
||||
end
|
||||
else
|
||||
slotWidget:setVisible(false)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local itemName = context.getItemNameById(self.itemId)
|
||||
local itemWidget = window:recursiveGetChildById("item")
|
||||
if itemWidget then
|
||||
itemWidget:setItemId(self.itemId)
|
||||
itemWidget:setImageSmooth(true)
|
||||
itemWidget:setItemCount(1)
|
||||
end
|
||||
|
||||
local itemInformation = window:recursiveGetChildById("titleInformation")
|
||||
if itemInformation then
|
||||
itemInformation:setText(context.capitalize(itemName))
|
||||
end
|
||||
end
|
||||
|
||||
function itemApi.onSelectSlot(widget)
|
||||
local slot = widget:getId()
|
||||
itemApi.onSelectImbuementSlot(widget.slot)
|
||||
local imbuement = self.activeSlots[slot]
|
||||
self.updateWindowState(imbuement)
|
||||
end
|
||||
|
||||
function itemApi.updateWindowState(imbuement)
|
||||
if imbuement and imbuement[1] and imbuement[1].id ~= 0 then
|
||||
context.imbuement:toggleMenu("clearImbue")
|
||||
self.window = context.imbuement.clearImbue
|
||||
self.onSelectSlotClear(imbuement)
|
||||
else
|
||||
context.imbuement:toggleMenu("selectImbue")
|
||||
self.window = context.imbuement.selectImbue
|
||||
self.onSelectSlotImbue()
|
||||
end
|
||||
end
|
||||
|
||||
function itemApi.onSelectImbuementSlot(slot)
|
||||
context.imbuement.clearImbue:recursiveGetChildById("slot"..self.selectedSlot):setBorderWidth(0)
|
||||
context.imbuement.selectImbue:recursiveGetChildById("slot"..self.selectedSlot):setBorderWidth(0)
|
||||
|
||||
self.selectedSlot = slot
|
||||
context.imbuement.clearImbue:recursiveGetChildById("slot"..slot):setBorderWidth(1)
|
||||
context.imbuement.clearImbue:recursiveGetChildById("slot"..slot):setBorderColor("white")
|
||||
context.imbuement.selectImbue:recursiveGetChildById("slot"..slot):setBorderWidth(1)
|
||||
context.imbuement.selectImbue:recursiveGetChildById("slot"..slot):setBorderColor("white")
|
||||
end
|
||||
|
||||
function itemApi:shutdown()
|
||||
self.window = nil
|
||||
self.itemId = 0
|
||||
self.tier = 0
|
||||
self.slots = 0
|
||||
self.activeSlots = {}
|
||||
self.availableImbuements = {}
|
||||
self.needItems = {}
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
end
|
||||
|
||||
if self.lastselectedwidget then
|
||||
self.lastselectedwidget:destroy()
|
||||
self.lastselectedwidget = nil
|
||||
end
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
function itemApi.onSelectSlotClear(imbuement)
|
||||
local title = self.window.cleanImbuePanel:getChildById("title")
|
||||
if title then
|
||||
title:setText(string.format('Clear Imbuement "%s"', imbuement[1].name))
|
||||
end
|
||||
|
||||
local cleanImbuementsDetails = self.window:recursiveGetChildById("cleanImbuementsDetails")
|
||||
if cleanImbuementsDetails then
|
||||
cleanImbuementsDetails:setText('')
|
||||
end
|
||||
|
||||
local timeRemaining = self.window:recursiveGetChildById("timeRemaining")
|
||||
if timeRemaining then
|
||||
local time = imbuement[1].duration or 0
|
||||
timeRemaining:setMinimum(0)
|
||||
timeRemaining:setMaximum(time)
|
||||
timeRemaining:setValue(imbuement[2], 0, time)
|
||||
end
|
||||
|
||||
local imbuementReqContent = self.window:recursiveGetChildById("imbuementReqContent")
|
||||
if imbuementReqContent then
|
||||
local hours = string.format("%02.f", math.floor(imbuement[2]/3600))
|
||||
local mins = string.format("%02.f", math.floor(imbuement[2]/60 - (hours*60)))
|
||||
|
||||
imbuementReqContent.time.textLabel:setText(string.format("%dh %dmin", hours, mins))
|
||||
imbuementReqContent.time.onHoverChange = function(widget, hovered, itemName, hasItem)
|
||||
if hovered then
|
||||
cleanImbuementsDetails:setText(tr("Show the time the imbuement is still active for."))
|
||||
else
|
||||
cleanImbuementsDetails:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local clearImbuementsList = self.window:recursiveGetChildById("clearImbuementsList")
|
||||
clearImbuementsList:destroyChildren()
|
||||
|
||||
local widget = g_ui.createWidget("SlotImbuing", clearImbuementsList)
|
||||
widget.resource:setImageSource("//images/game/imbuing/icons//" .. imbuement[1]["imageId"])
|
||||
widget:setBorderWidth(1)
|
||||
widget:setBorderColor("white")
|
||||
|
||||
local selectedImbuementContent = self.window:recursiveGetChildById("selectedImbuementContent")
|
||||
if selectedImbuementContent then
|
||||
local imbuementsDetails = selectedImbuementContent:recursiveGetChildById("imbuementsDetails")
|
||||
if imbuementsDetails then
|
||||
imbuementsDetails:setText(imbuement[1].description or "")
|
||||
end
|
||||
end
|
||||
|
||||
local balance = context.getPlayerBalance()
|
||||
local clearButton = self.window:recursiveGetChildById("clear")
|
||||
if clearButton then
|
||||
clearButton:setEnabled(balance >= imbuement[3])
|
||||
clearButton.onClick = function()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
context.imbuement.hide()
|
||||
|
||||
local function confirm()
|
||||
g_game.clearImbuement(self.selectedSlot)
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
|
||||
context.imbuement.show()
|
||||
end
|
||||
|
||||
local function cancelFunc()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
context.imbuement.show()
|
||||
end
|
||||
|
||||
self.confirmWindow = displayGeneralBox(tr('Confirm Clearing'), tr("Do you wish to spend %s gold coins to clear the imbuement \"%s\" from your item?", context.commaValue(imbuement[3]), context.capitalize(imbuement[1].name)),
|
||||
{ { text=tr('Yes'), callback=confirm },
|
||||
{ text=tr('No'), callback=cancelFunc },
|
||||
}, confirm, cancelFunc)
|
||||
end
|
||||
|
||||
if balance >= imbuement[3] then
|
||||
clearButton:setImageSource("/game_imbuing/images/clear")
|
||||
clearButton:setImageClip("0 0 128 66")
|
||||
else
|
||||
clearButton:setImageSource("/game_imbuing/images/imbue_empty")
|
||||
end
|
||||
|
||||
clearButton.onHoverChange = function(widget, hovered, itemName, hasItem)
|
||||
if hovered then
|
||||
cleanImbuementsDetails:setText(tr("Your needs have changed? Click here to clear the imbuement from your item for a fee."))
|
||||
else
|
||||
cleanImbuementsDetails:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local costPanel = self.window:recursiveGetChildById("costPanel")
|
||||
if costPanel then
|
||||
costPanel.cost:setText(context.commaValue(imbuement[3]))
|
||||
costPanel.cost:setColor(balance < imbuement[3] and "#C04040" or "#C0C0C0")
|
||||
end
|
||||
end
|
||||
|
||||
function itemApi.onSelectSlotImbue()
|
||||
self.selectBaseType('basicButton')
|
||||
|
||||
self.window:recursiveGetChildById('imbuementsDetails'):setVisible(false)
|
||||
end
|
||||
|
||||
function itemApi.selectBaseType(selectedButtonId)
|
||||
self.window:recursiveGetChildById('blockedPanels'):setVisible(true)
|
||||
local qualityAndImbuementContent = self.window:recursiveGetChildById("qualityAndImbuementContent")
|
||||
if not qualityAndImbuementContent then
|
||||
return
|
||||
end
|
||||
|
||||
local basicButton = qualityAndImbuementContent.basicButton
|
||||
local intricateButton = qualityAndImbuementContent.intricateButton
|
||||
local powerfullButton = qualityAndImbuementContent.powerfullButton
|
||||
|
||||
local selectedBaseType = 0
|
||||
for _, button in pairs({basicButton, intricateButton, powerfullButton}) do
|
||||
button:setOn(button:getId() == selectedButtonId)
|
||||
if button:getId() == selectedButtonId then
|
||||
selectedBaseType = button.baseImbuement or 0
|
||||
end
|
||||
end
|
||||
|
||||
local imbuementsList = self.window:recursiveGetChildById("imbuementsList")
|
||||
imbuementsList:setWidth(70)
|
||||
imbuementsList:destroyChildren()
|
||||
|
||||
local imbuementsDetails = self.window:recursiveGetChildById("imbuementsDetails")
|
||||
imbuementsDetails:setVisible(false)
|
||||
|
||||
local maxWidth = 0
|
||||
for id, imbuement in pairs(self.availableImbuements) do
|
||||
local imbuementType = imbuement.type
|
||||
if imbuementType == nil and imbuement.group then
|
||||
if imbuement.group == 'Basic' then imbuementType = 0
|
||||
elseif imbuement.group == 'Intricate' then imbuementType = 1
|
||||
elseif imbuement.group == 'Powerful' then imbuementType = 2
|
||||
end
|
||||
end
|
||||
if imbuementType == selectedBaseType then
|
||||
local widget = g_ui.createWidget("SlotImbuing", imbuementsList)
|
||||
widget:setId(tostring(id))
|
||||
widget.resource:setImageSource("//images/game/imbuing/icons//" .. imbuement.imageId)
|
||||
|
||||
widget.onClick = function()
|
||||
itemApi.selectImbuementWidget(widget, imbuement)
|
||||
end
|
||||
|
||||
maxWidth = math.min(imbuementsList.maxWidth, maxWidth + imbuementsList.incrementwidth)
|
||||
end
|
||||
end
|
||||
|
||||
imbuementsList:setWidth(maxWidth)
|
||||
end
|
||||
|
||||
function itemApi.onSelectImbuement(widget)
|
||||
local imbuementId = tonumber(widget:getId())
|
||||
local imbuement = self.availableImbuements[imbuementId]
|
||||
if not imbuement then
|
||||
return
|
||||
end
|
||||
|
||||
self.window:recursiveGetChildById('blockedPanels'):setVisible(false)
|
||||
|
||||
local imbuementReqPanel = self.window:recursiveGetChildById("imbuementReqPanel")
|
||||
if imbuementReqPanel then
|
||||
imbuementReqPanel.title:setText(string.format('Imbue Empty Slot with "%s"', imbuement.name))
|
||||
end
|
||||
local itensDetails = self.window:recursiveGetChildById("itensDetails")
|
||||
if itensDetails then
|
||||
itensDetails:setText("")
|
||||
end
|
||||
end
|
||||
|
||||
function itemApi.selectImbuementWidget(widget, imbuement)
|
||||
if self.lastselectedwidget then
|
||||
self.lastselectedwidget:setBorderWidth(1)
|
||||
self.lastselectedwidget:setBorderColorTop("#797979")
|
||||
self.lastselectedwidget:setBorderColorLeft("#797979")
|
||||
self.lastselectedwidget:setBorderColorRight("#2e2e2e")
|
||||
self.lastselectedwidget:setBorderColorBottom("#2e2e2e")
|
||||
end
|
||||
self.lastselectedwidget = widget
|
||||
widget:setBorderWidth(1)
|
||||
widget:setBorderColor("white")
|
||||
|
||||
self.onSelectImbuement(widget)
|
||||
|
||||
local imbuementsDetails = self.window:recursiveGetChildById("imbuementsDetails")
|
||||
if imbuementsDetails then
|
||||
imbuementsDetails:setVisible(true)
|
||||
imbuementsDetails:setText(imbuement.description or "")
|
||||
end
|
||||
|
||||
local requiredItems = self.window:recursiveGetChildById("requiredItems")
|
||||
local hasRequiredItems = true
|
||||
if requiredItems then
|
||||
for i = 1, 3 do
|
||||
local itemWidget = requiredItems:getChildById("item"..i)
|
||||
if itemWidget then
|
||||
local source = imbuement.sources[i]
|
||||
if source then
|
||||
itemWidget.item:setItemId(source.item:getId())
|
||||
itemWidget:setVisible(true)
|
||||
local itemCount = self.needItems[source.item:getId()] or 0
|
||||
itemWidget.count:setText(itemCount .."/" .. source.item:getCount())
|
||||
if itemCount >= source.item:getCount() then
|
||||
itemWidget.count:setColor("#C0C0C0")
|
||||
else
|
||||
hasRequiredItems = false
|
||||
itemWidget.count:setColor("#C04040")
|
||||
end
|
||||
|
||||
itemWidget.onHoverChange = function(widget, hovered)
|
||||
local itensDetails = self.window:recursiveGetChildById("itensDetails")
|
||||
if hovered then
|
||||
local itemCount = self.needItems[source.item:getId()] or 0
|
||||
if itemCount >= source.item:getCount() then
|
||||
itensDetails:setText(string.format("The imbuement you have selected requires %s.", source.description))
|
||||
else
|
||||
itensDetails:setText(string.format("The imbuement requires %s. Unfortunately you do not own the needed amount.", source.description))
|
||||
end
|
||||
else
|
||||
if itensDetails then
|
||||
itensDetails:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
else
|
||||
itemWidget:setVisible(false)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local costPanel = self.window:recursiveGetChildById("costPanel")
|
||||
if costPanel then
|
||||
local cost = imbuement.cost or 0
|
||||
costPanel.cost:setText(context.commaValue(cost))
|
||||
local balance = context.getPlayerBalance()
|
||||
|
||||
if balance < cost then
|
||||
hasRequiredItems = false
|
||||
end
|
||||
|
||||
costPanel.cost:setColor(balance < cost and "#C04040" or "#C0C0C0")
|
||||
end
|
||||
|
||||
local imbueApply = self.window:recursiveGetChildById("imbueApply")
|
||||
if imbueApply then
|
||||
imbueApply:setEnabled(hasRequiredItems)
|
||||
if not hasRequiredItems then
|
||||
imbueApply:setImageSource("/game_imbuing/images/imbue_empty")
|
||||
imbueApply:setImageClip("0 0 128 66")
|
||||
else
|
||||
imbueApply:setImageSource("/game_imbuing/images/imbue_green")
|
||||
end
|
||||
|
||||
imbueApply.onHoverChange = function(widget, hovered, itemName, hasItem)
|
||||
local itensDetails = self.window:recursiveGetChildById("itensDetails")
|
||||
if hovered then
|
||||
itensDetails:setText(tr("Apply the selected imbuement. This will consume the required astral sources and gold."))
|
||||
else
|
||||
if itensDetails then
|
||||
itensDetails:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
imbueApply.onClick = function()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
context.imbuement.hide()
|
||||
|
||||
local function confirm()
|
||||
g_game.applyImbuement(self.selectedSlot, imbuement.id)
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
|
||||
context.imbuement.show()
|
||||
end
|
||||
|
||||
local function cancelFunc()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
context.imbuement.show()
|
||||
end
|
||||
|
||||
self.confirmWindow = displayGeneralBox(tr('Confirm Imbuing'), tr("You are about to imbue your item with \"%s\". This will consume the required astral sources and %s\ngold coins. Do you wish to proceed?", context.capitalize(imbuement.name), context.commaValue(imbuement.cost)),
|
||||
{ { text=tr('Yes'), callback=confirm },
|
||||
{ text=tr('No'), callback=cancelFunc },
|
||||
}, confirm, cancelFunc)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return itemApi
|
||||
end
|
||||
247
modules/game_imbuing/new_design/classes/imbuementscroll.lua
Normal file
|
|
@ -0,0 +1,247 @@
|
|||
return function(context)
|
||||
local scrollApi = {
|
||||
window = nil,
|
||||
itemId = 51442,
|
||||
confirmWindow = nil,
|
||||
availableImbuements = {},
|
||||
needItems = {}
|
||||
}
|
||||
|
||||
scrollApi.__index = scrollApi
|
||||
|
||||
local self = scrollApi
|
||||
function scrollApi.setup(availableImbuements, needItems)
|
||||
self.availableImbuements = availableImbuements or {}
|
||||
self.needItems = needItems or {}
|
||||
self.window = context.imbuement.scrollImbue
|
||||
|
||||
local itemWidget = self.window:recursiveGetChildById("itemScroll")
|
||||
if itemWidget then
|
||||
itemWidget:setItemId(self.itemId)
|
||||
itemWidget:setImageSmooth(true)
|
||||
itemWidget:setItemCount(1)
|
||||
end
|
||||
|
||||
self.onSelectSlotImbue()
|
||||
end
|
||||
|
||||
function scrollApi:shutdown()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
end
|
||||
|
||||
self.window = nil
|
||||
self.confirmWindow = nil
|
||||
self.lastselectedwidget = nil
|
||||
self.availableImbuements = {}
|
||||
self.needItems = {}
|
||||
end
|
||||
|
||||
function scrollApi.onSelectSlotImbue()
|
||||
self.selectBaseType('powerfullButton')
|
||||
self.window:recursiveGetChildById('imbuementsDetails'):setVisible(false)
|
||||
end
|
||||
|
||||
function scrollApi.selectBaseType(selectedButtonId)
|
||||
local qualityAndImbuementContent = self.window:recursiveGetChildById("qualityAndImbuementContent")
|
||||
if not qualityAndImbuementContent then
|
||||
return
|
||||
end
|
||||
|
||||
local intricateButton = qualityAndImbuementContent.intricateButton
|
||||
local powerfullButton = qualityAndImbuementContent.powerfullButton
|
||||
|
||||
local selectedBaseType = 1
|
||||
for _, button in pairs({intricateButton, powerfullButton}) do
|
||||
button:setOn(button:getId() == selectedButtonId)
|
||||
if button:getId() == selectedButtonId then
|
||||
selectedBaseType = button.baseImbuement or 1
|
||||
end
|
||||
end
|
||||
|
||||
local imbuementsList = self.window:recursiveGetChildById("imbuementsList")
|
||||
imbuementsList:destroyChildren()
|
||||
|
||||
local imbuementsDetails = self.window:recursiveGetChildById("imbuementsDetails")
|
||||
imbuementsDetails:setVisible(false)
|
||||
|
||||
local selected = false
|
||||
local matchedCount = 0
|
||||
|
||||
for id, imbuement in ipairs(self.availableImbuements) do
|
||||
local imbuementType = imbuement.type
|
||||
if imbuementType == nil and imbuement.group then
|
||||
if imbuement.group == 'Basic' then imbuementType = 0
|
||||
elseif imbuement.group == 'Intricate' then imbuementType = 1
|
||||
elseif imbuement.group == 'Powerful' then imbuementType = 2
|
||||
end
|
||||
end
|
||||
|
||||
if imbuementType == selectedBaseType then
|
||||
matchedCount = matchedCount + 1
|
||||
local widget = g_ui.createWidget("SlotImbuing", imbuementsList)
|
||||
widget:setId(tostring(id))
|
||||
widget.resource:setImageSource("//images/game/imbuing/icons//" .. imbuement.imageId)
|
||||
|
||||
if not selected then
|
||||
scrollApi.selectImbuementWidget(widget, imbuement)
|
||||
selected = true
|
||||
end
|
||||
|
||||
widget.onClick = function()
|
||||
scrollApi.selectImbuementWidget(widget, imbuement)
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
function scrollApi.selectImbuementWidget(widget, imbuement)
|
||||
if self.lastselectedwidget then
|
||||
self.lastselectedwidget:setBorderWidth(1)
|
||||
self.lastselectedwidget:setBorderColorTop("#797979")
|
||||
self.lastselectedwidget:setBorderColorLeft("#797979")
|
||||
self.lastselectedwidget:setBorderColorRight("#2e2e2e")
|
||||
self.lastselectedwidget:setBorderColorBottom("#2e2e2e")
|
||||
end
|
||||
self.lastselectedwidget = widget
|
||||
widget:setBorderWidth(1)
|
||||
widget:setBorderColor("white")
|
||||
|
||||
self.onSelectImbuement(widget)
|
||||
|
||||
local imbuementsDetails = self.window:recursiveGetChildById("imbuementsDetails")
|
||||
if imbuementsDetails then
|
||||
imbuementsDetails:setVisible(true)
|
||||
imbuementsDetails:setText(imbuement.description or "")
|
||||
end
|
||||
|
||||
local requiredItems = self.window:recursiveGetChildById("requiredItems")
|
||||
local hasRequiredItems = true
|
||||
if requiredItems then
|
||||
for i = 1, 4 do
|
||||
local itemWidget = requiredItems:getChildById("item"..i)
|
||||
if itemWidget then
|
||||
local source = imbuement.sources[i]
|
||||
if source then
|
||||
itemWidget.item:setItemId(source.item:getId())
|
||||
itemWidget:setVisible(true)
|
||||
local itemCount = self.needItems[source.item:getId()] or 0
|
||||
itemWidget.count:setText(itemCount .."/" .. source.item:getCount())
|
||||
if itemCount >= source.item:getCount() then
|
||||
itemWidget.count:setColor("#C0C0C0")
|
||||
else
|
||||
hasRequiredItems = false
|
||||
itemWidget.count:setColor("#C04040")
|
||||
end
|
||||
|
||||
itemWidget.onHoverChange = function(widget, hovered)
|
||||
local itensDetails = self.window:recursiveGetChildById("itensDetails")
|
||||
if hovered then
|
||||
local itemCount = self.needItems[source.item:getId()] or 0
|
||||
if itemCount >= source.item:getCount() then
|
||||
itensDetails:setText(string.format("The imbuement you have selected requires %s.", source.description))
|
||||
else
|
||||
itensDetails:setText(string.format("The imbuement requires %s. Unfortunately you do not own the needed amount.", source.description))
|
||||
end
|
||||
else
|
||||
if itensDetails then
|
||||
itensDetails:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
else
|
||||
itemWidget:setVisible(false)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local costPanel = self.window:recursiveGetChildById("costPanel")
|
||||
if costPanel then
|
||||
local cost = imbuement.cost or 0
|
||||
costPanel.cost:setText(context.commaValue(cost))
|
||||
local balance = context.getPlayerBalance()
|
||||
|
||||
if balance < cost then
|
||||
hasRequiredItems = false
|
||||
end
|
||||
|
||||
costPanel.cost:setColor(balance < cost and "#C04040" or "#C0C0C0")
|
||||
end
|
||||
|
||||
local imbuescrollApply = self.window:recursiveGetChildById("imbuescrollApply")
|
||||
if imbuescrollApply then
|
||||
imbuescrollApply:setEnabled(hasRequiredItems)
|
||||
if not hasRequiredItems then
|
||||
imbuescrollApply:setImageSource("/game_imbuing/images/imbue_empty")
|
||||
imbuescrollApply:setImageClip("0 0 128 66")
|
||||
else
|
||||
imbuescrollApply:setImageSource("/game_imbuing/images/imbue_green")
|
||||
end
|
||||
|
||||
imbuescrollApply.onHoverChange = function(widget, hovered, itemName, hasItem)
|
||||
local itensDetails = self.window:recursiveGetChildById("itensDetails")
|
||||
if hovered then
|
||||
itensDetails:setText(tr("Apply the selected imbuement. This will consume the required astral sources and gold."))
|
||||
else
|
||||
if itensDetails then
|
||||
itensDetails:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
imbuescrollApply.onClick = function()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
context.imbuement.hide()
|
||||
|
||||
local function confirm()
|
||||
g_game.applyImbuement(0, imbuement.id)
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
|
||||
context.imbuement.show()
|
||||
end
|
||||
|
||||
local function cancelFunc()
|
||||
if self.confirmWindow then
|
||||
self.confirmWindow:destroy()
|
||||
self.confirmWindow = nil
|
||||
end
|
||||
|
||||
context.imbuement.show()
|
||||
end
|
||||
|
||||
self.confirmWindow = displayGeneralBox(tr('Confirm Imbuing'), tr("You are about to imbue your item with \"%s\". This will consume the required astral sources and %s\ngold coins. Do you wish to proceed?", context.capitalize(imbuement.name), context.commaValue(imbuement.cost)),
|
||||
{ { text=tr('Yes'), callback=confirm },
|
||||
{ text=tr('No'), callback=cancelFunc },
|
||||
}, confirm, cancelFunc)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function scrollApi.onSelectImbuement(widget)
|
||||
local imbuementId = tonumber(widget:getId())
|
||||
local imbuement = self.availableImbuements[imbuementId]
|
||||
if not imbuement then
|
||||
return
|
||||
end
|
||||
|
||||
|
||||
local imbuementReqPanel = self.window:recursiveGetChildById("imbuementReqPanel")
|
||||
if imbuementReqPanel then
|
||||
imbuementReqPanel.title:setText(string.format('Imbue Blank Scroll with "%s"', imbuement.name))
|
||||
end
|
||||
local itensDetails = self.window:recursiveGetChildById("itensDetails")
|
||||
if itensDetails then
|
||||
itensDetails:setText("")
|
||||
end
|
||||
end
|
||||
|
||||
return scrollApi
|
||||
end
|
||||
111
modules/game_imbuing/new_design/classes/imbuementselection.lua
Normal file
|
|
@ -0,0 +1,111 @@
|
|||
return function()
|
||||
local selectionApi = {
|
||||
pickItem = nil,
|
||||
isSelectingScroll = false,
|
||||
isSelecting = false,
|
||||
}
|
||||
|
||||
selectionApi.__index = selectionApi
|
||||
|
||||
local self = selectionApi
|
||||
|
||||
function selectionApi.startUp()
|
||||
self.pickItem = g_ui.createWidget('UIWidget')
|
||||
self.pickItem:setVisible(false)
|
||||
self.pickItem:setFocusable(false)
|
||||
self.pickItem.onMouseRelease = self.onChooseItemMouseRelease
|
||||
end
|
||||
|
||||
function selectionApi:shutdown()
|
||||
if self.pickItem then
|
||||
self.pickItem:ungrabMouse()
|
||||
self.pickItem:destroy()
|
||||
self.pickItem = nil
|
||||
end
|
||||
|
||||
if self.isSelecting then
|
||||
g_mouse.popCursor('target')
|
||||
end
|
||||
self.isSelectingScroll = false
|
||||
self.isSelecting = false
|
||||
end
|
||||
|
||||
function selectionApi:selectItem()
|
||||
if not self.pickItem then
|
||||
self:startUp()
|
||||
end
|
||||
|
||||
if g_mouse.isPressed() or self.isSelecting then
|
||||
return
|
||||
end
|
||||
|
||||
self.isSelectingScroll = false
|
||||
self.isSelecting = true
|
||||
self.pickItem:grabMouse()
|
||||
g_mouse.pushCursor('target')
|
||||
end
|
||||
|
||||
function selectionApi:selectScroll()
|
||||
if not self.pickItem then
|
||||
self:startUp()
|
||||
end
|
||||
|
||||
if g_mouse.isPressed() or self.isSelecting then
|
||||
return
|
||||
end
|
||||
|
||||
self.isSelectingScroll = true
|
||||
self.isSelecting = true
|
||||
self.pickItem:grabMouse()
|
||||
g_mouse.pushCursor('target')
|
||||
end
|
||||
|
||||
function selectionApi.onChooseItemMouseRelease(widget, mousePosition, mouseButton)
|
||||
local item = nil
|
||||
if mouseButton == MouseLeftButton then
|
||||
local clickedWidget = modules.game_interface.getRootPanel():recursiveGetChildByPos(mousePosition, false)
|
||||
if clickedWidget then
|
||||
if clickedWidget:getClassName() == 'UIGameMap' then
|
||||
local tile = clickedWidget:getTile(mousePosition)
|
||||
if tile then
|
||||
local thing = tile:getTopMoveThing()
|
||||
if thing and thing:isItem() then
|
||||
item = thing
|
||||
end
|
||||
end
|
||||
elseif clickedWidget:getClassName() == 'UIItem' and not clickedWidget:isVirtual() then
|
||||
item = clickedWidget:getItem()
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if item and item:isPickupable() then
|
||||
local pos = item:getPosition()
|
||||
local itemId = item:getId()
|
||||
local stackPos = item:getStackPos()
|
||||
|
||||
if self.isSelectingScroll then
|
||||
g_game.selectImbuementScroll()
|
||||
else
|
||||
g_game.selectImbuementItem(itemId, pos, stackPos)
|
||||
end
|
||||
|
||||
self.pickItem:ungrabMouse()
|
||||
g_mouse.popCursor('target')
|
||||
self.isSelectingScroll = false
|
||||
self.isSelecting = false
|
||||
|
||||
return true
|
||||
else
|
||||
modules.game_textmessage.displayFailureMessage(tr('Sorry, not possible.'))
|
||||
end
|
||||
|
||||
self.pickItem:ungrabMouse()
|
||||
g_mouse.popCursor('target')
|
||||
self.isSelectingScroll = false
|
||||
self.isSelecting = false
|
||||
return true
|
||||
end
|
||||
|
||||
return selectionApi
|
||||
end
|
||||
BIN
modules/game_imbuing/new_design/images/basic-button.png
Normal file
|
After Width: | Height: | Size: 9.1 KiB |
BIN
modules/game_imbuing/new_design/images/blocked-panel.png
Normal file
|
After Width: | Height: | Size: 20 KiB |
BIN
modules/game_imbuing/new_design/images/blocked-panels.png
Normal file
|
After Width: | Height: | Size: 30 KiB |
BIN
modules/game_imbuing/new_design/images/imbue-scroll-button.png
Normal file
|
After Width: | Height: | Size: 13 KiB |
BIN
modules/game_imbuing/new_design/images/imbuement-icons-64.png
Normal file
|
After Width: | Height: | Size: 65 KiB |
BIN
modules/game_imbuing/new_design/images/intricate-button.png
Normal file
|
After Width: | Height: | Size: 9.9 KiB |
BIN
modules/game_imbuing/new_design/images/pick-item-button.png
Normal file
|
After Width: | Height: | Size: 11 KiB |
BIN
modules/game_imbuing/new_design/images/powerfull-button.png
Normal file
|
After Width: | Height: | Size: 9.8 KiB |
112
modules/game_imbuing/new_design/main.lua
Normal file
|
|
@ -0,0 +1,112 @@
|
|||
local function commaValue(amount)
|
||||
if not amount then
|
||||
return "0"
|
||||
end
|
||||
|
||||
local formatted = tostring(amount)
|
||||
while true do
|
||||
local nextValue, changes = string.gsub(formatted, "^(-?%d+)(%d%d%d)", '%1,%2')
|
||||
formatted = nextValue
|
||||
if changes == 0 then
|
||||
break
|
||||
end
|
||||
end
|
||||
|
||||
return formatted
|
||||
end
|
||||
|
||||
local function capitalize(str)
|
||||
if not str or str == "" then
|
||||
return str
|
||||
end
|
||||
|
||||
return str:sub(1, 1):upper() .. str:sub(2)
|
||||
end
|
||||
|
||||
local function getPlayerBalance()
|
||||
local player = g_game.getLocalPlayer()
|
||||
if not player then
|
||||
return 0
|
||||
end
|
||||
|
||||
local bankGold = player:getResourceBalance(ResourceTypes.BANK_BALANCE) or 0
|
||||
local inventoryGold = player:getResourceBalance(ResourceTypes.GOLD_EQUIPPED) or 0
|
||||
return bankGold + inventoryGold
|
||||
end
|
||||
|
||||
local function getItemNameById(itemId)
|
||||
local itemType = g_things.getThingType(itemId, ThingCategoryItem)
|
||||
if itemType and itemType.getName and type(itemType.getName) == "function" then
|
||||
return itemType:getName() or "Unknown Item"
|
||||
end
|
||||
|
||||
return "Unknown Item"
|
||||
end
|
||||
|
||||
local context = {
|
||||
commaValue = commaValue,
|
||||
capitalize = capitalize,
|
||||
getPlayerBalance = getPlayerBalance,
|
||||
getItemNameById = getItemNameById,
|
||||
}
|
||||
|
||||
context.imbuement = dofile('t_imbui')(context)
|
||||
context.item = dofile('classes/imbuementitem')(context)
|
||||
context.scroll = dofile('classes/imbuementscroll')(context)
|
||||
context.selection = dofile('classes/imbuementselection')(context)
|
||||
|
||||
local api = {}
|
||||
|
||||
function api.init()
|
||||
return context.imbuement.init()
|
||||
end
|
||||
|
||||
function api.terminate()
|
||||
return context.imbuement.terminate()
|
||||
end
|
||||
|
||||
function api.close()
|
||||
return context.imbuement.close()
|
||||
end
|
||||
|
||||
function api.hide()
|
||||
return context.imbuement.hide()
|
||||
end
|
||||
|
||||
function api.onOpenImbuementWindow(...)
|
||||
return context.imbuement.onOpenImbuementWindow(...)
|
||||
end
|
||||
|
||||
function api.onImbuementItem(...)
|
||||
return context.imbuement.onImbuementItem(...)
|
||||
end
|
||||
|
||||
function api.onImbuementScroll(...)
|
||||
return context.imbuement.onImbuementScroll(...)
|
||||
end
|
||||
|
||||
function api.onMessageDialog(...)
|
||||
return context.imbuement.onMessageDialog(...)
|
||||
end
|
||||
|
||||
function api.onSelectItem()
|
||||
return context.imbuement.onSelectItem()
|
||||
end
|
||||
|
||||
function api.onSelectScroll()
|
||||
return context.imbuement.onSelectScroll()
|
||||
end
|
||||
|
||||
function api.onItemSlot(widget)
|
||||
return context.item.onSelectSlot(widget)
|
||||
end
|
||||
|
||||
function api.onItemBaseType(selectedButtonId)
|
||||
return context.item.selectBaseType(selectedButtonId)
|
||||
end
|
||||
|
||||
function api.onScrollBaseType(selectedButtonId)
|
||||
return context.scroll.selectBaseType(selectedButtonId)
|
||||
end
|
||||
|
||||
return api
|
||||
230
modules/game_imbuing/new_design/t_imbui.lua
Normal file
|
|
@ -0,0 +1,230 @@
|
|||
return function(context)
|
||||
local imbuementApi = {
|
||||
window = nil,
|
||||
selectItemOrScroll = nil,
|
||||
scrollImbue = nil,
|
||||
selectImbue = nil,
|
||||
clearImbue = nil,
|
||||
|
||||
messageWindow = nil,
|
||||
|
||||
bankGold = 0,
|
||||
inventoryGold = 0,
|
||||
}
|
||||
|
||||
imbuementApi.__index = imbuementApi
|
||||
|
||||
imbuementApi.MessageDialog = {
|
||||
ImbuementSuccess = 0,
|
||||
ImbuementError = 1,
|
||||
ImbuementRollFailed = 2,
|
||||
ImbuingStationNotFound = 3,
|
||||
ClearingCharmSuccess = 10,
|
||||
ClearingCharmError = 11,
|
||||
PreyMessage = 20,
|
||||
PreyError = 21,
|
||||
}
|
||||
|
||||
local self = imbuementApi
|
||||
|
||||
function imbuementApi.ensureWindow()
|
||||
if self.window then
|
||||
return
|
||||
end
|
||||
|
||||
self.window = g_ui.displayUI('t_imbui')
|
||||
self.selectItemOrScroll = self.window:recursiveGetChildById('selectItemOrScroll')
|
||||
self.scrollImbue = self.window:recursiveGetChildById('scrollImbue')
|
||||
self.selectImbue = self.window:recursiveGetChildById('selectImbue')
|
||||
self.clearImbue = self.window:recursiveGetChildById('clearImbue')
|
||||
self:hide()
|
||||
end
|
||||
|
||||
function imbuementApi.destroyWindow()
|
||||
self.selectItemOrScroll = nil
|
||||
self.scrollImbue = nil
|
||||
self.selectImbue = nil
|
||||
self.clearImbue = nil
|
||||
|
||||
if self.window then
|
||||
self.window:destroy()
|
||||
self.window = nil
|
||||
end
|
||||
end
|
||||
|
||||
function imbuementApi.init()
|
||||
end
|
||||
|
||||
function imbuementApi.terminate()
|
||||
if self.messageWindow then
|
||||
self.messageWindow:destroy()
|
||||
self.messageWindow = nil
|
||||
end
|
||||
|
||||
if context.item then
|
||||
context.item:shutdown()
|
||||
end
|
||||
if context.selection then
|
||||
context.selection:shutdown()
|
||||
end
|
||||
if context.scroll then
|
||||
context.scroll:shutdown()
|
||||
end
|
||||
self.destroyWindow()
|
||||
end
|
||||
|
||||
function imbuementApi.online()
|
||||
self:hide()
|
||||
if self.messageWindow then
|
||||
self.messageWindow:destroy()
|
||||
self.messageWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
function imbuementApi.offline()
|
||||
self:hide()
|
||||
if context.item then
|
||||
context.item:shutdown()
|
||||
end
|
||||
if context.scroll then
|
||||
context.scroll:shutdown()
|
||||
end
|
||||
if context.selection then
|
||||
context.selection:shutdown()
|
||||
end
|
||||
if self.messageWindow then
|
||||
self.messageWindow:destroy()
|
||||
self.messageWindow = nil
|
||||
end
|
||||
self.destroyWindow()
|
||||
end
|
||||
|
||||
function imbuementApi.show()
|
||||
self.ensureWindow()
|
||||
self.window:show(true)
|
||||
self.window:raise()
|
||||
self.window:focus()
|
||||
if self.messageWindow then
|
||||
self.messageWindow:destroy()
|
||||
self.messageWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
function imbuementApi.hide()
|
||||
if self.window then
|
||||
self.window:hide()
|
||||
end
|
||||
end
|
||||
|
||||
function imbuementApi.close()
|
||||
if g_game.isOnline() then
|
||||
g_game.closeImbuingWindow()
|
||||
end
|
||||
if self.window then
|
||||
self.window:hide()
|
||||
end
|
||||
end
|
||||
|
||||
function imbuementApi:toggleMenu(menu)
|
||||
for key, value in pairs(self) do
|
||||
if type(value) == 'userdata' and key ~= 'window' then
|
||||
if key == menu then
|
||||
value:show()
|
||||
if menu == 'selectItemOrScroll' then
|
||||
self.window:setHeight(388)
|
||||
elseif menu == 'scrollImbue' then
|
||||
self.window:setHeight(655)
|
||||
elseif menu == 'selectImbue' then
|
||||
self.window:setHeight(528)
|
||||
elseif menu == 'clearImbue' then
|
||||
self.window:setHeight(502)
|
||||
end
|
||||
else
|
||||
value:hide()
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function imbuementApi.onOpenImbuementWindow()
|
||||
self.ensureWindow()
|
||||
self:show()
|
||||
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
local bankGold = player:getResourceBalance(ResourceTypes.BANK_BALANCE) or 0
|
||||
local inventoryGold = player:getResourceBalance(ResourceTypes.GOLD_EQUIPPED) or 0
|
||||
local totalGold = bankGold + inventoryGold
|
||||
self.window.contentPanel.gold.gold:setText(context.commaValue(totalGold))
|
||||
end
|
||||
|
||||
self:toggleMenu("selectItemOrScroll")
|
||||
end
|
||||
|
||||
function imbuementApi.onImbuementItem(itemId, tier, slots, activeSlots, availableImbuements, needItems)
|
||||
self.ensureWindow()
|
||||
local needItemsTable = {}
|
||||
|
||||
for _, item in ipairs(needItems) do
|
||||
if item and item.getId then
|
||||
local itemId = item:getId()
|
||||
local count = item:getCount() or 0
|
||||
needItemsTable[itemId] = count
|
||||
end
|
||||
end
|
||||
|
||||
self:show()
|
||||
self:toggleMenu("selectImbue")
|
||||
context.item.setup(itemId, tier, slots, activeSlots, availableImbuements, needItemsTable)
|
||||
end
|
||||
|
||||
function imbuementApi.onImbuementScroll(availableImbuements, needItems)
|
||||
self.ensureWindow()
|
||||
local needItemsTable = {}
|
||||
|
||||
for _, item in ipairs(needItems) do
|
||||
if item and item.getId then
|
||||
local itemId = item:getId()
|
||||
local count = item:getCount() or 0
|
||||
needItemsTable[itemId] = count
|
||||
end
|
||||
end
|
||||
|
||||
self:toggleMenu("scrollImbue")
|
||||
context.scroll.setup(availableImbuements, needItemsTable)
|
||||
end
|
||||
|
||||
function imbuementApi.onSelectItem()
|
||||
self:hide()
|
||||
context.selection:selectItem()
|
||||
end
|
||||
|
||||
function imbuementApi.onSelectScroll()
|
||||
g_game.selectImbuementScroll()
|
||||
end
|
||||
|
||||
function imbuementApi.onMessageDialog(type, content)
|
||||
if type > imbuementApi.MessageDialog.ImbuingStationNotFound or not self.window or not self.window:isVisible() then
|
||||
return
|
||||
end
|
||||
|
||||
self:hide()
|
||||
if self.messageWindow then
|
||||
self.messageWindow:destroy()
|
||||
self.messageWindow = nil
|
||||
end
|
||||
|
||||
local function confirm()
|
||||
self.messageWindow:destroy()
|
||||
self.messageWindow = nil
|
||||
|
||||
imbuementApi.show()
|
||||
end
|
||||
|
||||
self.messageWindow = displayGeneralBox(tr('Message Dialog'), content or "",
|
||||
{ { text=tr('Ok'), callback=confirm },
|
||||
}, confirm, confirm)
|
||||
end
|
||||
|
||||
return imbuementApi
|
||||
end
|
||||
901
modules/game_imbuing/new_design/t_imbui.otui
Normal file
|
|
@ -0,0 +1,901 @@
|
|||
PickItemButton < UIButton
|
||||
id: itemButton
|
||||
size: 96 64
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
image-source: /game_imbuing/new_design/images/pick-item-button
|
||||
image-clip: 0 0 96 64
|
||||
@onClick: modules.game_imbuing.onSelectItem()
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 96 64
|
||||
$pressed:
|
||||
image-clip: 0 64 96 64
|
||||
|
||||
ScrollItemButton < UIButton
|
||||
id: scrollButton
|
||||
size: 96 64
|
||||
anchors.top: parent.top
|
||||
anchors.left: itemButton.right
|
||||
margin-left: 6
|
||||
image-source: /game_imbuing/new_design/images/imbue-scroll-button
|
||||
image-clip: 0 0 96 64
|
||||
@onClick: modules.game_imbuing.onSelectScroll()
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 96 64
|
||||
$pressed:
|
||||
image-clip: 0 64 96 64
|
||||
|
||||
SlotImbuing < UIButton
|
||||
size: 66 66
|
||||
border-width: 1
|
||||
border-color-top: #797979
|
||||
border-color-left: #797979
|
||||
border-color-bottom: #2e2e2e
|
||||
border-color-right: #2e2e2e
|
||||
$checked:
|
||||
border-color-top: #181818
|
||||
border-color-left: #181818
|
||||
border-color-bottom: #727272
|
||||
border-color-right: #727272
|
||||
UIWidget
|
||||
id: resource
|
||||
size: 64 64
|
||||
anchors.left: parent.left
|
||||
margin-left: 1
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
image-source: /game_imbuing/new_design/images/imbuement-icons-64
|
||||
image-clip: 0 0 64 64
|
||||
phantom: true
|
||||
|
||||
RequiredItem < UIWidget
|
||||
size: 66 90
|
||||
UIItem
|
||||
id: item
|
||||
size: 66 66
|
||||
anchors.left: parent.left
|
||||
anchors.top: parent.top
|
||||
priceable: false
|
||||
phantom: true
|
||||
image-source: /images/ui/item66
|
||||
draggable: false
|
||||
FlatLabel
|
||||
id: count
|
||||
margin-top: 3
|
||||
text-align: center
|
||||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/ui/infoPanel
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-offset: -2 1
|
||||
|
||||
SelectItemOrScroll < UIWidget
|
||||
anchors.fill: parent
|
||||
Panel
|
||||
id: itemOrScrollPanel
|
||||
height: 93
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 5
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Pick Item or Imbue a Blank Scroll')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: itemOrScrollContent
|
||||
anchors.fill: parent
|
||||
margin: 22 12 10 12
|
||||
PickItemButton
|
||||
ScrollItemButton
|
||||
|
||||
UIWidget
|
||||
id: blockedPanels
|
||||
size: 708 198
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /game_imbuing/new_design/images/blocked-panels
|
||||
margin-top: 11
|
||||
|
||||
SelectImbue < UIWidget
|
||||
anchors.fill: parent
|
||||
Panel
|
||||
id: itemOrScrollPanel
|
||||
height: 103
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 5
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Pick Item or Imbue a Blank Scroll')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: itemOrScrollContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 10 12
|
||||
PickItemButton
|
||||
ScrollItemButton
|
||||
|
||||
|
||||
Panel
|
||||
id: slots
|
||||
size: 208 66
|
||||
anchors.top: prev.top
|
||||
anchors.right: parent.right
|
||||
margin-top: -1
|
||||
margin-right: 18
|
||||
SlotImbuing
|
||||
id: slot0
|
||||
margin-right: 6
|
||||
&slot: 0
|
||||
anchors.right: next.left
|
||||
@onClick: modules.game_imbuing.onItemSlot(self)
|
||||
SlotImbuing
|
||||
id: slot1
|
||||
margin-right: 6
|
||||
anchors.right: next.left
|
||||
&slot: 1
|
||||
phantom: false
|
||||
@onClick: modules.game_imbuing.onItemSlot(self)
|
||||
SlotImbuing
|
||||
id: slot2
|
||||
&slot: 2
|
||||
anchors.right: parent.right
|
||||
@onClick: modules.game_imbuing.onItemSlot(self)
|
||||
|
||||
UIItem
|
||||
id: item
|
||||
size: 64 64
|
||||
anchors.top: prev.top
|
||||
anchors.right: prev.left
|
||||
priceable: false
|
||||
virtual: true
|
||||
margin-top: 1
|
||||
margin-right: 22
|
||||
phantom: true
|
||||
draggable: false
|
||||
Label
|
||||
id: titleInformation
|
||||
anchors.top: prev.top
|
||||
anchors.right: prev.left
|
||||
!text: tr('Item Information')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
margin-top: 24
|
||||
margin-right: 22
|
||||
|
||||
Panel
|
||||
id: qualityAndImbuementPanel
|
||||
height: 177
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 17
|
||||
margin-top: 11
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Select Quality and Imbuement')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: qualityAndImbuementContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 9 12
|
||||
UIButton
|
||||
id: basicButton
|
||||
size: 144 37
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
&baseImbuement: 0
|
||||
margin-left: 116
|
||||
image-source: /game_imbuing/new_design/images/basic-button
|
||||
image-clip: 0 0 144 37
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 144 37
|
||||
$pressed:
|
||||
image-clip: 0 37 144 37
|
||||
$on:
|
||||
image-clip: 0 37 144 37
|
||||
@onClick: modules.game_imbuing.onItemBaseType(self:getId())
|
||||
|
||||
UIButton
|
||||
id: intricateButton
|
||||
size: 144 37
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
&baseImbuement: 1
|
||||
margin-left: 11
|
||||
image-source: /game_imbuing/new_design/images/intricate-button
|
||||
image-clip: 0 0 144 37
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 144 37
|
||||
$pressed:
|
||||
image-clip: 0 37 144 37
|
||||
$on:
|
||||
image-clip: 0 37 144 37
|
||||
@onClick: modules.game_imbuing.onItemBaseType(self:getId())
|
||||
|
||||
UIButton
|
||||
id: powerfullButton
|
||||
size: 144 37
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
&baseImbuement: 2
|
||||
margin-left: 11
|
||||
image-source: /game_imbuing/new_design/images/powerfull-button
|
||||
image-clip: 0 0 144 37
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 144 37
|
||||
$pressed:
|
||||
image-clip: 0 37 144 37
|
||||
$on:
|
||||
image-clip: 0 37 144 37
|
||||
@onClick: modules.game_imbuing.onItemBaseType(self:getId())
|
||||
|
||||
ScrollablePanel
|
||||
id: imbuementsList
|
||||
height: 70
|
||||
width: 70
|
||||
&originalwidth: 680
|
||||
&maxWidth: 675
|
||||
&incrementwidth: 73
|
||||
anchors.top: prev.bottom
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 11
|
||||
layout:
|
||||
type: grid
|
||||
cell-spacing: 5
|
||||
cell-size: 66 66
|
||||
num-columns: 9
|
||||
num-rows: 3
|
||||
|
||||
Label
|
||||
id: imbuementsDetails
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
!text: tr('Raises your walking speed by 30. Lasts for 20h 0min while equipped.')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
|
||||
Panel
|
||||
id: imbuementReqPanel
|
||||
height: 141
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 17
|
||||
margin-top: 11
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Imbue Empty Slot with "Imbuement Name"')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: imbuementReqContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 10 12
|
||||
Panel
|
||||
id: requiredItems
|
||||
width: 210
|
||||
height: 90
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
RequiredItem
|
||||
id: item1
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
RequiredItem
|
||||
id: item2
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-left: 6
|
||||
RequiredItem
|
||||
id: item3
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-left: 6
|
||||
|
||||
UIWidget
|
||||
id: horizontalArrow
|
||||
size: 14 25
|
||||
anchors.left: prev.right
|
||||
anchors.verticalCenter: requiredItems.verticalCenter
|
||||
margin-left: 171
|
||||
image-source: /images/ui/right-arrow
|
||||
phantom: false
|
||||
|
||||
Label
|
||||
id: itensDetails
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
!text: tr('')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
visible: true
|
||||
|
||||
UIButton
|
||||
id: imbueApply
|
||||
size: 128 66
|
||||
anchors.top: requiredItems.top
|
||||
anchors.right: parent.right
|
||||
image-source: /game_imbuing/images/imbue_empty
|
||||
image-clip: 0 0 128 66
|
||||
$pressed:
|
||||
image-clip: 0 66 128 66
|
||||
|
||||
FlatLabel
|
||||
id: costPanel
|
||||
margin-top: 3
|
||||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/ui/infoPanel
|
||||
Label
|
||||
id: cost
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
anchors.top: parent.top
|
||||
margin-right: 5
|
||||
margin-top: 3
|
||||
text: 200
|
||||
text-align: center
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
UIWidget
|
||||
size: 9 9
|
||||
anchors.top: cost.top
|
||||
anchors.left: cost.right
|
||||
margin-top: 3
|
||||
margin-left: 2
|
||||
image-source: /images/game/cyclopedia/icons/icon-goldcoin
|
||||
|
||||
UIWidget
|
||||
id: blockedPanels
|
||||
size: 708 141
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.left
|
||||
image-source: /game_imbuing/new_design/images/blocked-panel
|
||||
visible: false
|
||||
|
||||
ClearImbue < UIWidget
|
||||
anchors.fill: parent
|
||||
Panel
|
||||
id: itemOrScrollPanel
|
||||
height: 103
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 5
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Pick Item or Imbue a Blank Scroll')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: itemOrScrollContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 10 12
|
||||
PickItemButton
|
||||
ScrollItemButton
|
||||
|
||||
Panel
|
||||
id: slots
|
||||
size: 208 66
|
||||
anchors.top: prev.top
|
||||
anchors.right: parent.right
|
||||
margin-top: -1
|
||||
margin-right: 18
|
||||
SlotImbuing
|
||||
id: slot0
|
||||
margin-right: 6
|
||||
&slot: 0
|
||||
anchors.right: next.left
|
||||
@onClick: modules.game_imbuing.onItemSlot(self)
|
||||
SlotImbuing
|
||||
id: slot1
|
||||
margin-right: 6
|
||||
anchors.right: next.left
|
||||
&slot: 1
|
||||
phantom: false
|
||||
@onClick: modules.game_imbuing.onItemSlot(self)
|
||||
SlotImbuing
|
||||
id: slot2
|
||||
&slot: 2
|
||||
anchors.right: parent.right
|
||||
@onClick: modules.game_imbuing.onItemSlot(self)
|
||||
|
||||
UIItem
|
||||
id: item
|
||||
size: 64 64
|
||||
anchors.top: prev.top
|
||||
anchors.right: prev.left
|
||||
priceable: false
|
||||
virtual: true
|
||||
phantom: true
|
||||
draggable: false
|
||||
margin-top: 1
|
||||
margin-right: 22
|
||||
Label
|
||||
id: titleInformation
|
||||
anchors.top: prev.top
|
||||
anchors.right: prev.left
|
||||
!text: tr('Item Information')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
margin-top: 24
|
||||
margin-right: 22
|
||||
|
||||
Panel
|
||||
id: selectedImbuementPanel
|
||||
height: 152
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 17
|
||||
margin-top: 11
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Selected Imbuement')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: selectedImbuementContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 9 12
|
||||
ScrollablePanel
|
||||
id: clearImbuementsList
|
||||
height: 70
|
||||
width: 70
|
||||
&originalwidth: 680
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 20
|
||||
layout:
|
||||
type: grid
|
||||
cell-spacing: 6
|
||||
cell-size: 66 66
|
||||
num-columns: 9
|
||||
num-rows: 3
|
||||
|
||||
Label
|
||||
id: imbuementsDetails
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
!text: tr('Raises your walking speed by 30. Lasts for 20h 0min while equipped.')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
|
||||
Panel
|
||||
id: cleanImbuePanel
|
||||
height: 141
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 17
|
||||
margin-top: 11
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Clear Imbuement "Imbuement Name"')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: imbuementReqContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 10 12
|
||||
Panel
|
||||
id: time
|
||||
size: 279 20
|
||||
image-source: /game_imbuing/images/imbui-timer-bg
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
margin-top: 34
|
||||
margin-left: 91
|
||||
phantom: false
|
||||
ProgressBarSD
|
||||
id: timeRemaining
|
||||
size: 277 18
|
||||
anchors.fill: parent
|
||||
image-source: /game_imbuing/images/imbui-progress
|
||||
margin: 1 1 1 1
|
||||
phantom: true
|
||||
percent: 1
|
||||
Label
|
||||
id: textLabel
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
text-align: center
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
margin-top: 2
|
||||
phantom: true
|
||||
|
||||
Label
|
||||
id: cleanImbuementsDetails
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
|
||||
UIButton
|
||||
id: clear
|
||||
size: 128 66
|
||||
anchors.top: parent.top
|
||||
anchors.right: parent.right
|
||||
image-source: /game_imbuing/images/clear
|
||||
image-clip: 0 0 128 66
|
||||
$pressed:
|
||||
image-clip: 0 66 128 66
|
||||
FlatLabel
|
||||
id: costPanel
|
||||
margin-top: 3
|
||||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/ui/infoPanel
|
||||
Label
|
||||
id: cost
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
anchors.top: parent.top
|
||||
margin-right: 5
|
||||
margin-top: 3
|
||||
text: 200
|
||||
text-align: center
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
UIWidget
|
||||
size: 9 9
|
||||
anchors.top: cost.top
|
||||
anchors.left: cost.right
|
||||
margin-top: 3
|
||||
margin-left: 2
|
||||
image-source: /images/game/cyclopedia/icons/icon-goldcoin
|
||||
|
||||
ScrollImbue < UIWidget
|
||||
anchors.fill: parent
|
||||
Panel
|
||||
id: itemOrScrollPanel
|
||||
height: 93
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 5
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Pick Item or Imbue a Blank Scroll')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: itemOrScrollContent
|
||||
anchors.fill: parent
|
||||
margin: 22 12 10 12
|
||||
PickItemButton
|
||||
ScrollItemButton
|
||||
|
||||
UIItem
|
||||
id: itemScroll
|
||||
size: 64 64
|
||||
anchors.top: prev.top
|
||||
anchors.right: parent.right
|
||||
priceable: false
|
||||
virtual: true
|
||||
draggable: false
|
||||
phantom: true
|
||||
margin-top: 1
|
||||
margin-right: 77
|
||||
|
||||
Label
|
||||
id: titleScroll
|
||||
anchors.top: prev.top
|
||||
anchors.right: prev.left
|
||||
!text: tr('Blank Imbuement Scroll')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
margin-top: 24
|
||||
margin-right: 22
|
||||
|
||||
Panel
|
||||
id: selectImbuementPanel
|
||||
height: 314
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 17
|
||||
margin-top: 11
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Select an Imbuement')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: qualityAndImbuementContent
|
||||
anchors.fill: parent
|
||||
margin: 22 12 9 12
|
||||
UIButton
|
||||
id: intricateButton
|
||||
size: 144 37
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
margin-left: 193
|
||||
&baseImbuement: 1
|
||||
image-source: /game_imbuing/new_design/images/intricate-button
|
||||
image-clip: 0 0 144 37
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 144 37
|
||||
$pressed:
|
||||
image-clip: 0 37 144 37
|
||||
$on:
|
||||
image-clip: 0 37 144 37
|
||||
@onClick: modules.game_imbuing.onScrollBaseType(self:getId())
|
||||
|
||||
UIButton
|
||||
id: powerfullButton
|
||||
size: 144 37
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-left: 11
|
||||
&baseImbuement: 2
|
||||
image-source: /game_imbuing/new_design/images/powerfull-button
|
||||
image-clip: 0 0 144 37
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 144 37
|
||||
$pressed:
|
||||
image-clip: 0 37 144 37
|
||||
$on:
|
||||
image-clip: 0 37 144 37
|
||||
@onClick: modules.game_imbuing.onScrollBaseType(self:getId())
|
||||
|
||||
ScrollablePanel
|
||||
id: imbuementsList
|
||||
height: 206
|
||||
width: 680
|
||||
anchors.top: prev.bottom
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 6
|
||||
padding-left: 25
|
||||
layout:
|
||||
type: grid
|
||||
cell-spacing: 4
|
||||
cell-size: 66 66
|
||||
num-columns: 9
|
||||
num-rows: 3
|
||||
Label
|
||||
id: imbuementsDetails
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
!text: tr('Raises your walking speed by 30. Lasts for 20h 0min while equipped.')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
text-wrap: true
|
||||
|
||||
Panel
|
||||
id: imbuementReqPanel
|
||||
height: 141
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 17
|
||||
margin-top: 11
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 2
|
||||
!text: tr('Imbue Blank Scroll with "Imbuement Name"')
|
||||
font: verdana-11px-rounded
|
||||
color: #AAAAAA
|
||||
text-auto-resize: true
|
||||
Panel
|
||||
id: imbuementReqContent
|
||||
anchors.fill: parent
|
||||
margin: 27 12 10 12
|
||||
Panel
|
||||
id: requiredItems
|
||||
width: 280
|
||||
height: 90
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
RequiredItem
|
||||
id: item1
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
RequiredItem
|
||||
id: item2
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-left: 6
|
||||
RequiredItem
|
||||
id: item3
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-left: 6
|
||||
RequiredItem
|
||||
id: item4
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-left: 6
|
||||
|
||||
UIWidget
|
||||
id: horizontalArrow
|
||||
size: 14 25
|
||||
anchors.left: prev.right
|
||||
anchors.verticalCenter: requiredItems.verticalCenter
|
||||
margin-left: 171
|
||||
image-source: /images/ui/right-arrow
|
||||
phantom: false
|
||||
|
||||
Label
|
||||
id: itensDetails
|
||||
anchors.bottom: parent.bottom
|
||||
anchors.left: parent.left
|
||||
!text: tr('')
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
visible: true
|
||||
|
||||
UIButton
|
||||
id: imbuescrollApply
|
||||
size: 128 66
|
||||
anchors.top: requiredItems.top
|
||||
anchors.right: parent.right
|
||||
image-source: /game_imbuing/images/imbue_empty
|
||||
image-clip: 0 0 128 66
|
||||
$pressed:
|
||||
image-clip: 0 0 128 66
|
||||
|
||||
FlatLabel
|
||||
id: costPanel
|
||||
margin-top: 3
|
||||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/ui/infoPanel
|
||||
Label
|
||||
id: cost
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
anchors.top: parent.top
|
||||
margin-right: 5
|
||||
margin-top: 3
|
||||
text: 200
|
||||
text-align: center
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
UIWidget
|
||||
size: 9 9
|
||||
anchors.top: cost.top
|
||||
anchors.left: cost.right
|
||||
margin-top: 3
|
||||
margin-left: 2
|
||||
image-source: /images/game/cyclopedia/icons/icon-goldcoin
|
||||
|
||||
NewMainWindow
|
||||
id: imbuingWindow
|
||||
!text: tr('Imbuement Shrine')
|
||||
size: 740 640
|
||||
@onEscape: modules.game_imbuing.close()
|
||||
Panel
|
||||
id: contentPanel
|
||||
anchors.fill: parent
|
||||
margin: 12 12 12 12
|
||||
|
||||
SelectItemOrScroll
|
||||
id: selectItemOrScroll
|
||||
main-window-size: 740 388
|
||||
visible: true
|
||||
|
||||
ScrollImbue
|
||||
id: scrollImbue
|
||||
main-window-size: 740 655
|
||||
visible: false
|
||||
|
||||
SelectImbue
|
||||
id: selectImbue
|
||||
main-window-size: 740 528
|
||||
visible: false
|
||||
|
||||
ClearImbue
|
||||
id: clearImbue
|
||||
main-window-size: 740 502
|
||||
visible: false
|
||||
|
||||
HorizontalSeparator
|
||||
id: bottomSep
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: close.top
|
||||
margin-bottom: 11
|
||||
Button
|
||||
id: close
|
||||
!text: tr('Close')
|
||||
size: 43 20
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
@onClick: modules.game_imbuing.close()
|
||||
Panel
|
||||
id: gold
|
||||
size: 160 20
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: parent.bottom
|
||||
image-source: /images/game/prey/balanceBg
|
||||
UIWidget
|
||||
id: goldIcon
|
||||
anchors.top: parent.top
|
||||
anchors.right: parent.right
|
||||
margin-top: 6
|
||||
margin-right: 3
|
||||
image-source: /images/game/prey/prey_gold
|
||||
UIWidget
|
||||
id: gold
|
||||
anchors.top: parent.top
|
||||
anchors.right: prev.left
|
||||
anchors.left: parent.left
|
||||
margin-top: 3
|
||||
margin-right: 2
|
||||
text-align: right
|
||||
text: 0
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
text-auto-resize: true
|
||||
BIN
modules/game_imbuing/old_design/images/100percent.png
Normal file
|
After Width: | Height: | Size: 3.8 KiB |
BIN
modules/game_imbuing/old_design/images/slot.png
Normal file
|
After Width: | Height: | Size: 2.3 KiB |
BIN
modules/game_imbuing/old_design/images/slot_inactive.png
Normal file
|
After Width: | Height: | Size: 1.6 KiB |
|
After Width: | Height: | Size: 8.7 KiB |
674
modules/game_imbuing/old_design/imbuing.lua
Normal file
|
|
@ -0,0 +1,674 @@
|
|||
local oldDesignApi = {}
|
||||
local imbuingWindow
|
||||
local bankGold = 0
|
||||
local inventoryGold = 0
|
||||
local itemImbuements = {}
|
||||
local emptyImbue
|
||||
local groupsCombo
|
||||
local imbueLevelsCombo
|
||||
local protectionBtn
|
||||
local clearImbue
|
||||
local selectedImbue
|
||||
local imbueItems = {}
|
||||
local protection = false
|
||||
local clearConfirmWindow
|
||||
local imbueConfirmWindow
|
||||
local infoPanel
|
||||
|
||||
local setProtection
|
||||
local resetSlots
|
||||
local selectSlot
|
||||
local hide
|
||||
local show
|
||||
local toggle
|
||||
local formatTooltipText
|
||||
local setupTooltipEvents
|
||||
local function destroyWindow()
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
|
||||
if imbueConfirmWindow then
|
||||
imbueConfirmWindow:destroy()
|
||||
imbueConfirmWindow = nil
|
||||
end
|
||||
|
||||
if imbuingWindow then
|
||||
imbuingWindow:destroy()
|
||||
imbuingWindow = nil
|
||||
end
|
||||
|
||||
emptyImbue = nil
|
||||
groupsCombo = nil
|
||||
imbueLevelsCombo = nil
|
||||
protectionBtn = nil
|
||||
clearImbue = nil
|
||||
infoPanel = nil
|
||||
selectedImbue = nil
|
||||
itemImbuements = {}
|
||||
imbueItems = {}
|
||||
protection = false
|
||||
end
|
||||
|
||||
local function ensureWindow()
|
||||
if imbuingWindow then
|
||||
return
|
||||
end
|
||||
|
||||
imbuingWindow = g_ui.displayUI('imbuing')
|
||||
emptyImbue = imbuingWindow.emptyImbue
|
||||
groupsCombo = emptyImbue.groups
|
||||
imbueLevelsCombo = emptyImbue.imbuement
|
||||
protectionBtn = emptyImbue.protection
|
||||
clearImbue = imbuingWindow.clearImbue
|
||||
infoPanel = imbuingWindow.infoPanel
|
||||
imbuingWindow:hide()
|
||||
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
bankGold = player:getResourceBalance(ResourceTypes.BANK_BALANCE)
|
||||
inventoryGold = player:getResourceBalance(ResourceTypes.GOLD_EQUIPPED)
|
||||
imbuingWindow.balance:setText(tr(comma_value (player:getTotalMoney())))
|
||||
end
|
||||
|
||||
groupsCombo.onOptionChange = function(widget)
|
||||
imbueLevelsCombo:clearOptions()
|
||||
if itemImbuements ~= nil then
|
||||
local selectedGroup = groupsCombo:getCurrentOption().text
|
||||
for _, imbuement in ipairs(itemImbuements) do
|
||||
if imbuement['group'] == selectedGroup then
|
||||
emptyImbue.imbuement:addOption(imbuement['name'])
|
||||
end
|
||||
end
|
||||
imbueLevelsCombo.onOptionChange(imbueLevelsCombo) -- update options
|
||||
end
|
||||
end
|
||||
|
||||
imbueLevelsCombo.onOptionChange = function(widget)
|
||||
setProtection(false)
|
||||
local selectedGroup = groupsCombo:getCurrentOption().text
|
||||
for _, imbuement in ipairs(itemImbuements) do
|
||||
if imbuement['group'] == selectedGroup then
|
||||
if #imbuement['sources'] == widget.currentIndex then
|
||||
selectedImbue = imbuement
|
||||
local hasAllItems = true
|
||||
|
||||
for i, source in ipairs(imbuement['sources']) do
|
||||
local itemFound = false
|
||||
for _, item in ipairs(imbueItems) do
|
||||
if item:getId() == source['item']:getId() then
|
||||
itemFound = true
|
||||
if item:getCount() >= source['item']:getCount() then
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setColor('white')
|
||||
else
|
||||
hasAllItems = false
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setColor('red')
|
||||
end
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setText(item:getCount() .. '/' .. source['item']:getCount())
|
||||
end
|
||||
end
|
||||
if not itemFound then
|
||||
hasAllItems = false
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setText('0/' .. source['item']:getCount())
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setColor('red')
|
||||
end
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setItemId(source['item']:getId())
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setTooltip('The imbuement requires ' .. source['description'] .. '.')
|
||||
end
|
||||
|
||||
for i = 3, widget.currentIndex + 1, -1 do
|
||||
emptyImbue.requiredItems:getChildByIndex(i).count:setText('')
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setItemId(0)
|
||||
emptyImbue.requiredItems:getChildByIndex(i).item:setTooltip('')
|
||||
end
|
||||
emptyImbue.protectionCost:setText((comma_value(imbuement['protectionCost'])))
|
||||
emptyImbue.cost:setText(comma_value(imbuement['cost']))
|
||||
|
||||
-- Verificar se tem todos os itens e gold suficiente
|
||||
local hasEnoughGold = false
|
||||
if not protection then
|
||||
hasEnoughGold = (bankGold + inventoryGold) >= imbuement['cost']
|
||||
if not hasEnoughGold then
|
||||
emptyImbue.cost:setColor('red')
|
||||
else
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
else
|
||||
hasEnoughGold = (bankGold + inventoryGold) >= (imbuement['cost'] + imbuement['protectionCost'])
|
||||
if not hasEnoughGold then
|
||||
emptyImbue.cost:setColor('red')
|
||||
else
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
end
|
||||
|
||||
-- Habilitar/desabilitar botão de imbue baseado em itens E gold
|
||||
if hasAllItems and hasEnoughGold then
|
||||
emptyImbue.imbue:setEnabled(true)
|
||||
emptyImbue.imbue:setImageSource('/game_imbuing/images/imbue_green')
|
||||
else
|
||||
emptyImbue.imbue:setEnabled(false)
|
||||
emptyImbue.imbue:setImageSource('/game_imbuing/images/imbue_empty')
|
||||
end
|
||||
|
||||
-- Verificar se o botão de proteção deve ser desabilitado
|
||||
if (bankGold + inventoryGold) < imbuement['protectionCost'] then
|
||||
protectionBtn:setEnabled(false)
|
||||
emptyImbue.protection:setImageSource('/game_imbuing/old_design/images/useprotection-disabled')
|
||||
emptyImbue.protectionCost:setColor('red')
|
||||
else
|
||||
protectionBtn:setEnabled(true)
|
||||
emptyImbue.protection:setImageSource('/game_imbuing/old_design/images/100percent')
|
||||
emptyImbue.protectionCost:setColor('white')
|
||||
end
|
||||
emptyImbue.successRate:setText(imbuement['successRate'] .. '%')
|
||||
if selectedImbue['successRate'] > 50 then
|
||||
emptyImbue.successRate:setColor('white')
|
||||
else
|
||||
emptyImbue.successRate:setColor('red')
|
||||
end
|
||||
emptyImbue.description:setText(imbuement['description'])
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
protectionBtn.onClick = function()
|
||||
setProtection(not protection)
|
||||
end
|
||||
|
||||
-- Configurar hover events para exibir tooltips no painel
|
||||
setupTooltipEvents()
|
||||
end
|
||||
|
||||
|
||||
local function getCorrectIconId(id)
|
||||
local iconId = id
|
||||
if iconId >= 16 then iconId = iconId + 3 end -- pula 16, 17, 18
|
||||
if iconId >= 22 then iconId = iconId + 3 end -- pula 22, 23, 24
|
||||
if iconId >= 43 then iconId = iconId + 3 end -- pula 43, 44, 45
|
||||
if iconId >= 61 then iconId = iconId + 3 end -- pula 61, 62, 63
|
||||
if iconId >= 79 then iconId = iconId + 3 end -- pula 79, 80, 81
|
||||
return iconId
|
||||
end
|
||||
|
||||
function oldDesignApi.init()
|
||||
end
|
||||
|
||||
setProtection = function(value)
|
||||
protection = value
|
||||
if protection then
|
||||
if not selectedImbue then
|
||||
protection = false
|
||||
return
|
||||
end
|
||||
emptyImbue.cost:setText(comma_value(selectedImbue['cost'] + selectedImbue['protectionCost']))
|
||||
emptyImbue.successRate:setText('100%')
|
||||
emptyImbue.successRate:setColor('green')
|
||||
protectionBtn:setImageClip(torect('66 0 66 66'))
|
||||
|
||||
-- Verificar se há gold suficiente para o custo total com proteção
|
||||
if (bankGold + inventoryGold) < (selectedImbue['cost'] + selectedImbue['protectionCost']) then
|
||||
emptyImbue.cost:setColor('red')
|
||||
else
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
else
|
||||
if selectedImbue then
|
||||
emptyImbue.cost:setText(comma_value(selectedImbue['cost']))
|
||||
emptyImbue.successRate:setText(selectedImbue['successRate'] .. '%')
|
||||
if selectedImbue['successRate'] > 50 then
|
||||
emptyImbue.successRate:setColor('white')
|
||||
else
|
||||
emptyImbue.successRate:setColor('red')
|
||||
end
|
||||
|
||||
-- Verificar se há gold suficiente para o custo sem proteção
|
||||
if (bankGold + inventoryGold) < selectedImbue['cost'] then
|
||||
emptyImbue.cost:setColor('red')
|
||||
else
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
protectionBtn:setImageClip(torect('0 0 66 66'))
|
||||
end
|
||||
end
|
||||
|
||||
-- Re-verificar o estado do botão de imbue quando a proteção mudar
|
||||
if selectedImbue then
|
||||
local hasAllItems = true
|
||||
for i, source in ipairs(selectedImbue['sources']) do
|
||||
local itemFound = false
|
||||
for _, item in ipairs(imbueItems) do
|
||||
if item:getId() == source['item']:getId() then
|
||||
itemFound = true
|
||||
if item:getCount() < source['item']:getCount() then
|
||||
hasAllItems = false
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if not itemFound then
|
||||
hasAllItems = false
|
||||
break
|
||||
end
|
||||
end
|
||||
|
||||
local hasEnoughGold = false
|
||||
if protection then
|
||||
hasEnoughGold = (bankGold + inventoryGold) >= (selectedImbue['cost'] + selectedImbue['protectionCost'])
|
||||
else
|
||||
hasEnoughGold = (bankGold + inventoryGold) >= selectedImbue['cost']
|
||||
end
|
||||
|
||||
-- Habilitar/desabilitar botão de imbue baseado em itens E gold
|
||||
if hasAllItems and hasEnoughGold then
|
||||
emptyImbue.imbue:setEnabled(true)
|
||||
emptyImbue.imbue:setImageSource('/game_imbuing/images/imbue_green')
|
||||
else
|
||||
emptyImbue.imbue:setEnabled(false)
|
||||
emptyImbue.imbue:setImageSource('/game_imbuing/images/imbue_empty')
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function oldDesignApi.terminate()
|
||||
destroyWindow()
|
||||
end
|
||||
|
||||
resetSlots = function()
|
||||
emptyImbue:setVisible(false)
|
||||
clearImbue:setVisible(false)
|
||||
if infoPanel then
|
||||
local tooltipContent = infoPanel:recursiveGetChildById('tooltipContent')
|
||||
if tooltipContent then tooltipContent:setText('') end
|
||||
end
|
||||
for i = 1, 3 do
|
||||
local slot = imbuingWindow.itemInfo.slots:getChildByIndex(i)
|
||||
slot:setText('Slot ' .. i)
|
||||
slot:getChildById('icon'):setVisible(false)
|
||||
slot:setEnabled(false)
|
||||
slot:setTooltip(
|
||||
'Items can have up to three imbuements slots. This slot is not available for this item.')
|
||||
slot.onClick = nil
|
||||
end
|
||||
end
|
||||
|
||||
selectSlot = function(widget, slotId, activeSlot)
|
||||
local slotIcon = widget:getChildById('icon')
|
||||
|
||||
if activeSlot then
|
||||
emptyImbue:setVisible(false)
|
||||
widget:setText('')
|
||||
slotIcon:setVisible(true)
|
||||
local id = activeSlot[1]['id'] or 1
|
||||
slotIcon:setImageSource('//images/game/imbuing/icons//' .. getCorrectIconId(id))
|
||||
slotIcon:setImageClip(torect('0 0 64 64'))
|
||||
clearImbue.title:setText('Clear Imbuement "' .. activeSlot[1]['name'] .. '"')
|
||||
clearImbue.groups:clearOptions()
|
||||
clearImbue.groups:addOption(activeSlot[1]['group'])
|
||||
clearImbue.imbuement:clearOptions()
|
||||
clearImbue.imbuement:addOption(activeSlot[1]['name'])
|
||||
clearImbue.description:setText(activeSlot[1]['description'])
|
||||
|
||||
local hours = string.format('%02.f', math.floor(activeSlot[2] / 3600))
|
||||
local mins = string.format('%02.f', math.floor(activeSlot[2] / 60 - (hours * 60)))
|
||||
|
||||
local totalTime = activeSlot[1].duration or 72000
|
||||
local timeRemaining = clearImbue.time.timerContainer.timeRemaining
|
||||
|
||||
if timeRemaining then
|
||||
timeRemaining:setMinimum(0)
|
||||
timeRemaining:setMaximum(totalTime)
|
||||
timeRemaining:setValue(activeSlot[2], 0, totalTime)
|
||||
end
|
||||
|
||||
clearImbue.time.timerContainer.timeRemaining.text:setText(hours .. ':' .. mins .. 'h')
|
||||
clearImbue.cost:setText(comma_value(activeSlot[3]))
|
||||
if (bankGold + inventoryGold) < activeSlot[3] then
|
||||
clearImbue.clear:setEnabled(false)
|
||||
clearImbue.clear:setImageSource('/game_imbuing/images/imbue_empty')
|
||||
clearImbue.cost:setColor('red')
|
||||
end
|
||||
|
||||
local yesCallback = function()
|
||||
g_game.clearImbuement(slotId)
|
||||
widget:setText('Slot ' .. (slotId + 1))
|
||||
slotIcon:setVisible(true)
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
end
|
||||
local noCallback = function()
|
||||
imbuingWindow:show()
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
clearImbue.clear.onClick = function()
|
||||
imbuingWindow:hide()
|
||||
clearConfirmWindow = displayGeneralBox(tr('Confirm Clearing'),
|
||||
tr(
|
||||
'Do you wish to spend ' .. activeSlot[3] ..
|
||||
' gold coins to clear the imbuement "' ..
|
||||
activeSlot[1]['name'] .. '" from your item?'), {
|
||||
{
|
||||
text = tr('Yes'),
|
||||
callback = yesCallback
|
||||
},
|
||||
{
|
||||
text = tr('No'),
|
||||
callback = noCallback
|
||||
},
|
||||
anchor = AnchorHorizontalCenter
|
||||
}, yesCallback, noCallback)
|
||||
end
|
||||
|
||||
clearImbue:setVisible(true)
|
||||
else
|
||||
emptyImbue:setVisible(true)
|
||||
clearImbue:setVisible(false)
|
||||
|
||||
local yesCallback = function()
|
||||
g_game.applyImbuement(slotId, selectedImbue['id'], protection)
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
slotIcon:setVisible(true)
|
||||
local id = selectedImbue['id'] or 1
|
||||
slotIcon:setImageSource('//images/game/imbuing/icons//' .. getCorrectIconId(id))
|
||||
imbuingWindow:show()
|
||||
end
|
||||
local noCallback = function()
|
||||
imbuingWindow:show()
|
||||
if clearConfirmWindow then
|
||||
clearConfirmWindow:destroy()
|
||||
clearConfirmWindow = nil
|
||||
end
|
||||
end
|
||||
|
||||
emptyImbue.imbue.onClick = function()
|
||||
imbuingWindow:hide()
|
||||
local cost = selectedImbue['cost']
|
||||
local successRate = selectedImbue['successRate']
|
||||
if protection then
|
||||
cost = cost + selectedImbue['protectionCost']
|
||||
successRate = '100'
|
||||
end
|
||||
clearConfirmWindow = displayGeneralBox(tr('Confirm Imbuing Attempt'),
|
||||
'You are about to imbue your item with "' .. selectedImbue['name'] ..
|
||||
'".\nYour chance to succeed is ' .. successRate ..
|
||||
'%. It will consume the required astral sources and ' .. cost ..
|
||||
' gold coins.\nDo you wish to proceed?', {
|
||||
{
|
||||
text = tr('Yes'),
|
||||
callback = yesCallback
|
||||
},
|
||||
{
|
||||
text = tr('No'),
|
||||
callback = noCallback
|
||||
},
|
||||
anchor = AnchorHorizontalCenter
|
||||
}, yesCallback, noCallback)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function oldDesignApi.onImbuementItem(itemId, tier, slots, activeSlots, imbuements, needItems)
|
||||
if not itemId then
|
||||
return
|
||||
end
|
||||
ensureWindow()
|
||||
resetSlots()
|
||||
imbueItems = table.copy(needItems)
|
||||
imbuingWindow.itemInfo.item:setItemId(itemId)
|
||||
|
||||
for i = 1, slots do
|
||||
local slot = imbuingWindow.itemInfo.slots:getChildByIndex(i)
|
||||
slot.onClick = function(widget)
|
||||
selectSlot(widget, i - 1)
|
||||
end
|
||||
slot:setTooltip(
|
||||
'Use this slot to imbue your item. Depending on the item you can have up to three different imbuements.')
|
||||
slot:setEnabled(true)
|
||||
|
||||
if slot:getId() == 'slot0' then
|
||||
selectSlot(slot, i - 1)
|
||||
end
|
||||
end
|
||||
|
||||
for i, slot in pairs(activeSlots) do
|
||||
local activeSlotBtn = imbuingWindow.itemInfo.slots:getChildById('slot' .. i)
|
||||
activeSlotBtn.onClick = function(widget)
|
||||
selectSlot(widget, i, slot)
|
||||
end
|
||||
|
||||
-- Atualiza o ícone de todos os slots ativos imediatamente
|
||||
local slotIcon = activeSlotBtn:getChildById('icon')
|
||||
activeSlotBtn:setText('')
|
||||
slotIcon:setVisible(true)
|
||||
local id = slot[1]['id'] or 1
|
||||
slotIcon:setImageSource('//images/game/imbuing/icons//' .. getCorrectIconId(id))
|
||||
|
||||
if activeSlotBtn:getId() == 'slot0' then
|
||||
selectSlot(activeSlotBtn, i, slot)
|
||||
end
|
||||
end
|
||||
|
||||
if imbuements ~= nil then
|
||||
groupsCombo:clearOptions()
|
||||
imbueLevelsCombo:clearOptions()
|
||||
itemImbuements = table.copy(imbuements)
|
||||
for _, imbuement in ipairs(itemImbuements) do
|
||||
if not groupsCombo:isOption(imbuement['group']) then
|
||||
groupsCombo:addOption(imbuement['group'])
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- Reconfigurar eventos de hover após carregar os slots
|
||||
setupTooltipEvents()
|
||||
show()
|
||||
end
|
||||
|
||||
function oldDesignApi.onResourcesBalanceChange(balance, oldBalance, type)
|
||||
if type == ResourceTypes.BANK_BALANCE then
|
||||
bankGold = balance
|
||||
elseif type == ResourceTypes.GOLD_EQUIPPED then
|
||||
inventoryGold = balance
|
||||
end
|
||||
if not imbuingWindow then
|
||||
return
|
||||
end
|
||||
local player = g_game.getLocalPlayer()
|
||||
if player then
|
||||
if type == ResourceTypes.BANK_BALANCE or type == ResourceTypes.GOLD_EQUIPPED then
|
||||
imbuingWindow.balance:setText(tr(comma_value (player:getTotalMoney())))
|
||||
|
||||
-- Re-verificar o estado dos botões quando o saldo mudar
|
||||
if selectedImbue and emptyImbue:isVisible() then
|
||||
-- Verificar botão de proteção
|
||||
if (bankGold + inventoryGold) < selectedImbue['protectionCost'] then
|
||||
protectionBtn:setEnabled(false)
|
||||
emptyImbue.protection:setImageSource('/game_imbuing/old_design/images/useprotection-disabled')
|
||||
emptyImbue.protectionCost:setColor('red')
|
||||
else
|
||||
protectionBtn:setEnabled(true)
|
||||
emptyImbue.protection:setImageSource('/game_imbuing/old_design/images/100percent')
|
||||
emptyImbue.protectionCost:setColor('white')
|
||||
end
|
||||
|
||||
-- Verificar se tem todos os itens
|
||||
local hasAllItems = true
|
||||
for i, source in ipairs(selectedImbue['sources']) do
|
||||
local itemFound = false
|
||||
for _, item in ipairs(imbueItems) do
|
||||
if item:getId() == source['item']:getId() then
|
||||
itemFound = true
|
||||
if item:getCount() < source['item']:getCount() then
|
||||
hasAllItems = false
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if not itemFound then
|
||||
hasAllItems = false
|
||||
break
|
||||
end
|
||||
end
|
||||
|
||||
-- Verificar gold suficiente
|
||||
local hasEnoughGold = false
|
||||
if protection then
|
||||
hasEnoughGold = (bankGold + inventoryGold) >= (selectedImbue['cost'] + selectedImbue['protectionCost'])
|
||||
if not hasEnoughGold then
|
||||
emptyImbue.cost:setColor('red')
|
||||
else
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
else
|
||||
hasEnoughGold = (bankGold + inventoryGold) >= selectedImbue['cost']
|
||||
if not hasEnoughGold then
|
||||
emptyImbue.cost:setColor('red')
|
||||
else
|
||||
emptyImbue.cost:setColor('white')
|
||||
end
|
||||
end
|
||||
|
||||
-- Habilitar/desabilitar botão de imbue baseado em itens E gold
|
||||
if hasAllItems and hasEnoughGold then
|
||||
emptyImbue.imbue:setEnabled(true)
|
||||
emptyImbue.imbue:setImageSource('/game_imbuing/images/imbue_green')
|
||||
else
|
||||
emptyImbue.imbue:setEnabled(false)
|
||||
emptyImbue.imbue:setImageSource('/game_imbuing/images/imbue_empty')
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function oldDesignApi.onCloseImbuementWindow()
|
||||
if not imbuingWindow then
|
||||
return
|
||||
end
|
||||
resetSlots()
|
||||
destroyWindow()
|
||||
end
|
||||
|
||||
hide = function()
|
||||
if g_game.isOnline() then
|
||||
g_game.closeImbuingWindow()
|
||||
end
|
||||
if imbuingWindow then
|
||||
imbuingWindow:hide()
|
||||
end
|
||||
end
|
||||
|
||||
show = function()
|
||||
ensureWindow()
|
||||
imbuingWindow:show()
|
||||
imbuingWindow:raise()
|
||||
imbuingWindow:focus()
|
||||
end
|
||||
|
||||
toggle = function()
|
||||
ensureWindow()
|
||||
if imbuingWindow:isVisible() then
|
||||
return hide()
|
||||
end
|
||||
show()
|
||||
end
|
||||
|
||||
-- Função para formatar texto com quebra de linha automática
|
||||
formatTooltipText = function(text)
|
||||
if not text then return '' end
|
||||
|
||||
-- Definir largura máxima aproximada (em caracteres)
|
||||
local maxWidth = 240
|
||||
|
||||
local formattedText = ''
|
||||
local currentLine = ''
|
||||
|
||||
-- Dividir o texto em palavras
|
||||
for word in text:gmatch("%S+") do
|
||||
-- Se adicionar a palavra exceder a largura máxima
|
||||
if #currentLine + #word + 1 > maxWidth and #currentLine > 0 then
|
||||
formattedText = formattedText .. currentLine .. '\n'
|
||||
currentLine = word
|
||||
else
|
||||
if #currentLine > 0 then
|
||||
currentLine = currentLine .. ' ' .. word
|
||||
else
|
||||
currentLine = word
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- Adicionar a última linha
|
||||
if #currentLine > 0 then
|
||||
formattedText = formattedText .. currentLine
|
||||
end
|
||||
|
||||
return formattedText
|
||||
end
|
||||
|
||||
-- Função para configurar eventos de hover em elementos com tooltip
|
||||
setupTooltipEvents = function()
|
||||
if not infoPanel then return end
|
||||
|
||||
local tooltipContent = infoPanel:recursiveGetChildById('tooltipContent')
|
||||
if not tooltipContent then return end
|
||||
|
||||
-- Função para adicionar hover a um widget
|
||||
local function addHoverToWidget(widget)
|
||||
if not widget or not widget.getTooltip then return end
|
||||
|
||||
widget.onHoverChange = function(self, hovered)
|
||||
if hovered then
|
||||
local tooltip = self:getTooltip()
|
||||
if tooltip and tooltip ~= '' then
|
||||
-- Adicionar quebras de linha para textos longos
|
||||
local formattedText = formatTooltipText(tooltip)
|
||||
tooltipContent:setText(formattedText)
|
||||
else
|
||||
tooltipContent:setText('')
|
||||
end
|
||||
else
|
||||
tooltipContent:setText('')
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- Adicionar hover aos botões principais
|
||||
if emptyImbue.imbue then addHoverToWidget(emptyImbue.imbue) end
|
||||
if emptyImbue.protection then addHoverToWidget(emptyImbue.protection) end
|
||||
if clearImbue.clear then addHoverToWidget(clearImbue.clear) end
|
||||
|
||||
-- Adicionar hover aos itens requeridos
|
||||
if emptyImbue.requiredItems then
|
||||
for i = 1, 3 do
|
||||
local item = emptyImbue.requiredItems:getChildByIndex(i).item
|
||||
if item then addHoverToWidget(item) end
|
||||
end
|
||||
end
|
||||
|
||||
-- Adicionar hover aos slots
|
||||
if imbuingWindow.itemInfo and imbuingWindow.itemInfo.slots then
|
||||
for i = 1, 3 do
|
||||
local slot = imbuingWindow.itemInfo.slots:getChildByIndex(i)
|
||||
if slot then addHoverToWidget(slot) end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
oldDesignApi.hide = hide
|
||||
oldDesignApi.close = hide
|
||||
oldDesignApi.show = show
|
||||
oldDesignApi.toggle = toggle
|
||||
|
||||
return oldDesignApi
|
||||
|
|
@ -1,11 +1,18 @@
|
|||
Slot < Button
|
||||
width: 70
|
||||
width: 66
|
||||
height: 66
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
enabled: false
|
||||
text-wrap: true
|
||||
!tooltip: tr('Items can have up to three imbuements slots. This slot is not available for this item.')
|
||||
|
||||
UIWidget
|
||||
id: icon
|
||||
size: 64 64
|
||||
anchors.centerIn: parent
|
||||
phantom: true
|
||||
visible: false
|
||||
|
||||
RequiredItem < Panel
|
||||
width: 66
|
||||
height: 90
|
||||
|
|
@ -16,6 +23,7 @@ RequiredItem < Panel
|
|||
width: 66
|
||||
anchors.left: parent.left
|
||||
anchors.top: parent.top
|
||||
image-source: /images/ui/item66
|
||||
|
||||
FlatLabel
|
||||
id: count
|
||||
|
|
@ -24,11 +32,14 @@ RequiredItem < Panel
|
|||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
text-offset: 0 0
|
||||
image-source: /images/ui/infoPanel
|
||||
|
||||
ItemInformation < Panel
|
||||
height: 100
|
||||
border: 1 black
|
||||
padding: 5
|
||||
padding: 3
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage
|
||||
image-border: 5
|
||||
|
||||
Label
|
||||
id: title
|
||||
|
|
@ -62,13 +73,26 @@ ItemInformation < Panel
|
|||
!text: tr("Slot 1")
|
||||
text-align: center
|
||||
anchors.left: parent.left
|
||||
image-source: /game_imbuing/old_design/images/slot_inactive
|
||||
image-clip: 0 0 66 66
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 66 66
|
||||
$pressed:
|
||||
image-source: /game_imbuing/old_design/images/slot
|
||||
image-clip: 0 0 66 66
|
||||
|
||||
Slot
|
||||
id: slot1
|
||||
!text: tr("Slot 2")
|
||||
text-align: center
|
||||
margin-left: 10
|
||||
anchors.left: prev.right
|
||||
margin-left: 10
|
||||
image-source: /game_imbuing/old_design/images/slot_inactive
|
||||
image-clip: 0 0 66 66
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 66 66
|
||||
$pressed:
|
||||
image-source: /game_imbuing/old_design/images/slot
|
||||
image-clip: 0 0 66 66
|
||||
|
||||
Slot
|
||||
id: slot2
|
||||
|
|
@ -76,6 +100,13 @@ ItemInformation < Panel
|
|||
text-align: center
|
||||
margin-left: 10
|
||||
anchors.left: prev.right
|
||||
image-source: /game_imbuing/old_design/images/slot_inactive
|
||||
image-clip: 0 0 66 66
|
||||
$hover !pressed:
|
||||
image-clip: 0 0 66 66
|
||||
$pressed:
|
||||
image-source: /game_imbuing/old_design/images/slot
|
||||
image-clip: 0 0 66 66
|
||||
|
||||
Label
|
||||
id: selectSlot
|
||||
|
|
@ -86,8 +117,9 @@ ItemInformation < Panel
|
|||
|
||||
EmptyImbue < Panel
|
||||
height: 240
|
||||
border: 1 black
|
||||
padding: 5
|
||||
padding: 3 15 15 15
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage_2
|
||||
image-border: 5
|
||||
|
||||
Label
|
||||
id: title
|
||||
|
|
@ -126,6 +158,7 @@ EmptyImbue < Panel
|
|||
anchors.bottom: prev.bottom
|
||||
anchors.left: parent.left
|
||||
!text: tr('Requires the following astral sources:')
|
||||
margin-bottom: 10
|
||||
|
||||
Label
|
||||
id: successRate
|
||||
|
|
@ -168,7 +201,7 @@ EmptyImbue < Panel
|
|||
height: 66
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
image-source: /images/game/imbuing/100percent
|
||||
image-source: /game_imbuing/old_design/images/100percent
|
||||
image-clip: 0 0 66 66
|
||||
margin-left: 15
|
||||
!tooltip: ("Bribe the fates! Click here to raise your chance to 100%. For guaranteed success use gold.")
|
||||
|
|
@ -180,6 +213,7 @@ EmptyImbue < Panel
|
|||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/ui/infoPanel
|
||||
|
||||
UIWidget
|
||||
id: horizontalArrow
|
||||
|
|
@ -199,7 +233,7 @@ EmptyImbue < Panel
|
|||
height: 66
|
||||
anchors.top: requiredItems.top
|
||||
anchors.right: parent.right
|
||||
image-source: /images/game/imbuing/imbue_empty
|
||||
image-source: /game_imbuing/images/imbue_empty
|
||||
image-clip: 0 0 128 66
|
||||
margin-left: 15
|
||||
!tooltip: tr("Click here to carry out the selected imbuement. This will consume the required astral sources and gold.")
|
||||
|
|
@ -214,11 +248,13 @@ EmptyImbue < Panel
|
|||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/game/prey/balanceBg
|
||||
|
||||
ClearImbue < Panel
|
||||
height: 240
|
||||
border: 1 black
|
||||
padding: 5
|
||||
padding: 3 15 15 15
|
||||
image-source: /images/ui/t2pixel-up-frame-borderimage_2
|
||||
image-border: 5
|
||||
|
||||
Label
|
||||
id: title
|
||||
|
|
@ -267,19 +303,35 @@ ClearImbue < Panel
|
|||
|
||||
Panel
|
||||
id: time
|
||||
width: 210
|
||||
width: 277
|
||||
height: 90
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: parent.bottom
|
||||
|
||||
Panel
|
||||
id: timerContainer
|
||||
size: 277 18
|
||||
anchors.centerIn: parent
|
||||
image-source: /game_imbuing/images/imbui-timer-bg
|
||||
|
||||
ProgressBarSD
|
||||
id: timeRemaining
|
||||
size: 277 18
|
||||
anchors.fill: parent
|
||||
image-source: /game_imbuing/images/imbui-progress
|
||||
margin: 1
|
||||
phantom: true
|
||||
percent: 1
|
||||
|
||||
FlatLabel
|
||||
id: timeRemaining
|
||||
size: 86 25
|
||||
margin-bottom: 20
|
||||
text-align: center
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
Label
|
||||
id: text
|
||||
anchors.centerIn: parent
|
||||
text-align: center
|
||||
text-auto-resize: true
|
||||
color: white
|
||||
font: verdana-11px-rounded
|
||||
margin-top: 1
|
||||
phantom: true
|
||||
|
||||
UIButton
|
||||
id: clear
|
||||
|
|
@ -287,7 +339,7 @@ ClearImbue < Panel
|
|||
height: 66
|
||||
anchors.top: time.top
|
||||
anchors.right: parent.right
|
||||
image-source: /images/game/imbuing/clear
|
||||
image-source: /game_imbuing/images/clear
|
||||
image-clip: 0 0 128 66
|
||||
margin-left: 15
|
||||
!tooltip: tr("Your needs have changed? Click here to clear the imbuement from your item for a fee.")
|
||||
|
|
@ -302,12 +354,29 @@ ClearImbue < Panel
|
|||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.top: prev.bottom
|
||||
image-source: /images/game/prey/balanceBg
|
||||
|
||||
infoPanelTolltip < Panel
|
||||
height: 75
|
||||
padding: 10
|
||||
image-source: /images/ui/2pixel_up_frame_borderimage
|
||||
image-border: 5
|
||||
|
||||
Label
|
||||
id: tooltipContent
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
text-align: left
|
||||
color: white
|
||||
font: verdana-11px-rounded
|
||||
text-wrap: true
|
||||
|
||||
MainWindow
|
||||
id: imbuingWindow
|
||||
!text: tr('Imbue Item')
|
||||
size: 550 430
|
||||
size: 572 520
|
||||
background-color: #AAAAAA
|
||||
@onEscape: modules.game_imbuing.hide()
|
||||
|
||||
|
|
@ -330,6 +399,13 @@ MainWindow
|
|||
anchors.top: emptyImbue.top
|
||||
anchors.right: parent.right
|
||||
|
||||
infoPanelTolltip
|
||||
id: infoPanel
|
||||
anchors.left: parent.left
|
||||
anchors.top: emptyImbue.bottom
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
|
||||
Button
|
||||
id: close
|
||||
!text: tr('Close')
|
||||
|
|
@ -341,6 +417,14 @@ MainWindow
|
|||
Label
|
||||
id: balance
|
||||
height: 25
|
||||
anchors.right: prev.left
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: parent.bottom
|
||||
text-align: right
|
||||
text-offset: -20 0
|
||||
image-source: /images/game/prey/balanceBg
|
||||
UIWidget
|
||||
id: Icon
|
||||
anchors.right: parent.right
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
margin-right: 4
|
||||
image-source: /game_cyclopedia/images/icon-goldcoin
|
||||
|
|
@ -630,7 +630,12 @@ function createThingMenu(menuPosition, lookThing, useThing, creatureThing)
|
|||
if lookThing:isCreature() then
|
||||
g_game.inspectCharacter(lookThing:getId(), InspectCreaturesTypes.INSPECT_CREATURE)
|
||||
elseif canInspect then
|
||||
g_game.inspectionNormalObject(lookThing:getPosition())
|
||||
local pos = lookThing:getPosition()
|
||||
if pos and pos:isValid() then
|
||||
g_game.inspectionNormalObject(pos)
|
||||
else
|
||||
g_game.inspectionObject(InspectObjectTypes.INSPECT_CYCLOPEDIA, lookThing:getId())
|
||||
end
|
||||
end
|
||||
end, shortcut)
|
||||
end
|
||||
|
|
@ -2061,4 +2066,4 @@ function toggleFocus(value, reason)
|
|||
gameLeftPanel:setFocusable(value)
|
||||
gameRightExtraPanel:setFocusable(value)
|
||||
gameLeftExtraPanel:setFocusable(value)
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -96,7 +96,7 @@ function init()
|
|||
onGameStart = onGameStart,
|
||||
onDestinyWheel = WheelOfDestiny.onDestinyWheel,
|
||||
--onUnlockGem = GemAtelier.onUnlockGem, --disabled because it's in TODO
|
||||
onResourceBalance = onResourceBalance,
|
||||
onResourcesBalanceChange = onResourceBalance,
|
||||
})
|
||||
|
||||
if modules.game_mainpanel then
|
||||
|
|
@ -112,7 +112,7 @@ function terminate()
|
|||
onGameStart = onGameStart,
|
||||
onDestinyWheel = WheelOfDestiny.onDestinyWheel,
|
||||
--onUnlockGem = GemAtelier.onUnlockGem, --disabled because it's in TODO
|
||||
onResourceBalance = onResourceBalance
|
||||
onResourcesBalanceChange = onResourceBalance
|
||||
})
|
||||
|
||||
if wheelWindow then
|
||||
|
|
|
|||
|
|
@ -1888,6 +1888,22 @@ void Game::closeImbuingWindow()
|
|||
m_protocolGame->sendCloseImbuingWindow();
|
||||
}
|
||||
|
||||
void Game::selectImbuementItem(const uint16_t itemId, const Position& pos, const uint8_t stackpos)
|
||||
{
|
||||
if (!canPerformGameAction())
|
||||
return;
|
||||
|
||||
m_protocolGame->sendImbuementWindowAction(Otc::IMBUEMENT_WINDOW_SELECT_ITEM, itemId, pos, stackpos);
|
||||
}
|
||||
|
||||
void Game::selectImbuementScroll()
|
||||
{
|
||||
if (!canPerformGameAction())
|
||||
return;
|
||||
|
||||
m_protocolGame->sendImbuementWindowAction(Otc::IMBUEMENT_WINDOW_SCROLL);
|
||||
}
|
||||
|
||||
void Game::imbuementDurations(const bool isOpen)
|
||||
{
|
||||
if (!canPerformGameAction())
|
||||
|
|
|
|||
|
|
@ -408,6 +408,8 @@ public:
|
|||
void clearImbuement(uint8_t slot);
|
||||
void closeImbuingWindow();
|
||||
void imbuementDurations(bool isOpen = false);
|
||||
void selectImbuementItem(uint16_t itemId, const Position& pos, uint8_t stackpos);
|
||||
void selectImbuementScroll();
|
||||
|
||||
// weapon proficiency related
|
||||
void sendWeaponProficiencyAction(uint8_t actionType, uint16_t itemId = 0);
|
||||
|
|
|
|||
|
|
@ -384,6 +384,8 @@ void Client::registerLuaFunctions()
|
|||
g_lua.bindSingletonFunction("g_game", "applyImbuement", &Game::applyImbuement, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "clearImbuement", &Game::clearImbuement, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "closeImbuingWindow", &Game::closeImbuingWindow, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "selectImbuementItem", &Game::selectImbuementItem, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "selectImbuementScroll", &Game::selectImbuementScroll, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "isUsingProtobuf", &Game::isUsingProtobuf, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "enableTileThingLuaCallback", &Game::enableTileThingLuaCallback, &g_game);
|
||||
g_lua.bindSingletonFunction("g_game", "isTileThingLuaCallbackEnabled", &Game::isTileThingLuaCallbackEnabled, &g_game);
|
||||
|
|
|
|||
|
|
@ -148,6 +148,7 @@ public:
|
|||
void sendApplyImbuement(uint8_t slot, uint32_t imbuementId, bool protectionCharm);
|
||||
void sendClearImbuement(uint8_t slot);
|
||||
void sendCloseImbuingWindow();
|
||||
void sendImbuementWindowAction(uint8_t type, uint16_t itemId = 0, const Position& pos = Position(), uint8_t stackpos = 0);
|
||||
void sendOpenRewardWall();
|
||||
void sendOpenRewardHistory();
|
||||
void sendGetRewardDaily(const uint8_t bonusShrine, const std::map<uint16_t, uint8_t>& items);
|
||||
|
|
|
|||
|
|
@ -5912,53 +5912,70 @@ Imbuement ProtocolGame::getImbuementInfo(const InputMessagePtr& msg)
|
|||
|
||||
void ProtocolGame::parseImbuementWindow(const InputMessagePtr& msg)
|
||||
{
|
||||
const bool isModernImbuementWindow = g_game.getClientVersion() >= 1510;
|
||||
uint8_t windowType = Otc::IMBUEMENT_WINDOW_SELECT_ITEM;
|
||||
if (g_game.getClientVersion() >= 1510) {
|
||||
if (isModernImbuementWindow) {
|
||||
windowType = static_cast<Otc::Imbuement_Window_t>(msg->getU8()); // window type
|
||||
msg->getU8(); // unknown byte
|
||||
if (std::cmp_greater(windowType, static_cast<uint8_t>(Otc::IMBUEMENT_WINDOW_SCROLL))) {
|
||||
g_logger.warning(fmt::format("ProtocolGame::parseImbuementWindow: unexpected windowType {}", windowType));
|
||||
return;
|
||||
}
|
||||
}
|
||||
switch (windowType) {
|
||||
case Otc::IMBUEMENT_WINDOW_CHOICE: {
|
||||
if (isModernImbuementWindow) {
|
||||
msg->getU8(); // unknown
|
||||
}
|
||||
const uint16_t itemId = msg->getU16(); // item client ID
|
||||
const uint32_t unknown = msg->getU32(); // unknown
|
||||
|
||||
g_lua.callGlobalField("g_game", "onOpenImbuementWindow", itemId, unknown);
|
||||
break;
|
||||
}
|
||||
case Otc::IMBUEMENT_WINDOW_SCROLL: {
|
||||
msg->getU8(); // unknown byte
|
||||
msg->getU8(); // unknown byte
|
||||
if (isModernImbuementWindow) {
|
||||
msg->getU8(); // unknown byte
|
||||
}
|
||||
const uint16_t imbuementsSize = msg->getU16();
|
||||
std::vector<Imbuement> imbuements;
|
||||
for (auto i = 0; i < imbuementsSize; ++i) {
|
||||
imbuements.reserve(imbuementsSize);
|
||||
for (uint16_t i = 0; std::cmp_less(i, imbuementsSize); ++i) {
|
||||
imbuements.push_back(getImbuementInfo(msg));
|
||||
}
|
||||
const uint32_t neededItemsListCount = msg->getU32();
|
||||
std::vector<ItemPtr> neededItemsList;
|
||||
neededItemsList.reserve(neededItemsListCount);
|
||||
for (uint32_t i = 0; i < neededItemsListCount; ++i) {
|
||||
for (uint32_t i = 0; std::cmp_less(i, neededItemsListCount); ++i) {
|
||||
const uint16_t needItemId = msg->getU16();
|
||||
const uint16_t count = msg->getU16();
|
||||
const auto& needItem = Item::create(needItemId);
|
||||
needItem->setCount(count);
|
||||
neededItemsList.push_back(needItem);
|
||||
}
|
||||
|
||||
g_lua.callGlobalField("g_game", "onImbuementScroll", imbuements, neededItemsList);
|
||||
break;
|
||||
}
|
||||
case Otc::IMBUEMENT_WINDOW_SELECT_ITEM: {
|
||||
const uint16_t itemId = msg->getU16(); // item client ID
|
||||
uint16_t itemId = 0;
|
||||
uint8_t tier = 0;
|
||||
if (isModernImbuementWindow) {
|
||||
msg->getU8(); // unknown
|
||||
}
|
||||
itemId = msg->getU16(); // item client ID
|
||||
const auto& thing = g_things.getThingType(itemId, ThingCategoryItem);
|
||||
if (isModernImbuementWindow && !thing) {
|
||||
throw Exception("ProtocolGame::parseImbuementWindow: unable to resolve thing type for item id {}", itemId);
|
||||
}
|
||||
if (thing) {
|
||||
const uint16_t classification = thing->getClassification();
|
||||
if (classification > 0) {
|
||||
msg->getU8(); // upgradeClass
|
||||
if (std::cmp_greater(classification, 0)) {
|
||||
tier = msg->getU8();
|
||||
}
|
||||
}
|
||||
const uint8_t slot = msg->getU8();
|
||||
const uint8_t slots = msg->getU8();
|
||||
std::unordered_map<int, std::tuple<Imbuement, uint32_t, uint32_t>> activeSlots;
|
||||
for (auto i = 0; i < slot; i++) {
|
||||
for (uint8_t i = 0; std::cmp_less(i, slots); ++i) {
|
||||
const uint8_t firstByte = msg->getU8();
|
||||
if (firstByte == 0x01) {
|
||||
Imbuement imbuement = getImbuementInfo(msg);
|
||||
|
|
@ -5969,20 +5986,21 @@ void ProtocolGame::parseImbuementWindow(const InputMessagePtr& msg)
|
|||
}
|
||||
const uint16_t imbuementsSize = msg->getU16();
|
||||
std::vector<Imbuement> imbuements;
|
||||
for (auto i = 0; i < imbuementsSize; ++i) {
|
||||
imbuements.reserve(imbuementsSize);
|
||||
for (uint16_t i = 0; std::cmp_less(i, imbuementsSize); ++i) {
|
||||
imbuements.push_back(getImbuementInfo(msg));
|
||||
}
|
||||
const uint32_t neededItemsListCount = msg->getU32();
|
||||
std::vector<ItemPtr> neededItemsList;
|
||||
neededItemsList.reserve(neededItemsListCount);
|
||||
for (uint32_t i = 0; i < neededItemsListCount; ++i) {
|
||||
for (uint32_t i = 0; std::cmp_less(i, neededItemsListCount); ++i) {
|
||||
const uint16_t needItemId = msg->getU16();
|
||||
const uint16_t count = msg->getU16();
|
||||
const auto& needItem = Item::create(needItemId);
|
||||
needItem->setCount(count);
|
||||
neededItemsList.push_back(needItem);
|
||||
}
|
||||
g_lua.callGlobalField("g_game", "onImbuementWindow", itemId, slot, activeSlots, imbuements, neededItemsList);
|
||||
g_lua.callGlobalField("g_game", "onImbuementItem", itemId, tier, slots, activeSlots, imbuements, neededItemsList);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1550,6 +1550,21 @@ void ProtocolGame::sendCloseImbuingWindow()
|
|||
send(msg);
|
||||
}
|
||||
|
||||
void ProtocolGame::sendImbuementWindowAction(const uint8_t type, const uint16_t itemId, const Position& pos, const uint8_t stackpos)
|
||||
{
|
||||
const auto& msg = std::make_shared<OutputMessage>();
|
||||
msg->addU8(Proto::ClientImbuementWindowAction);
|
||||
msg->addU8(type); // 1 = SELECT_ITEM, 2 = SCROLL
|
||||
|
||||
if (type == Otc::IMBUEMENT_WINDOW_SELECT_ITEM) {
|
||||
addPosition(msg, pos);
|
||||
msg->addU16(itemId);
|
||||
msg->addU8(stackpos);
|
||||
}
|
||||
|
||||
send(msg);
|
||||
}
|
||||
|
||||
void ProtocolGame::sendOpenRewardWall()
|
||||
{
|
||||
const auto& msg = std::make_shared<OutputMessage>();
|
||||
|
|
@ -1627,7 +1642,6 @@ void ProtocolGame::sendImbuementDurations(const bool isOpen)
|
|||
send(msg);
|
||||
}
|
||||
|
||||
|
||||
void ProtocolGame::sendQuickLoot(const uint8_t variant, const Position& pos, const uint16_t itemId, const uint8_t stackpos)
|
||||
{
|
||||
const auto msg = std::make_shared<OutputMessage>();
|
||||
|
|
|
|||