Use new coding style in game modules

Lots of refactoring and changes
Remove docs folder
master
Eduardo Bart 12 years ago
parent 1c3e630237
commit c54cd1fdf1

3
doc/.gitignore vendored

@ -1,3 +0,0 @@
*.yardoc
doc
!.gitignore

@ -1,222 +0,0 @@
# Style Tags Overview
## Style Overview
This document describes how style tags can be specified, how they affect your
widgets, and how to use specific built-in style tags in otclient, as well
as how to define new custom style tags.
## Style Value Types
{valhead:Integer}
Integer number, used by most of style proprieties
**Examples:**
* 1
* 9
* 5
{valhead:Float}
Float number
**Examples:**
* 1.0
* 9
* 1.5
{valhead:String}
String containing a text
**Examples:**
* this is a string
* it doesn't need quotes or escaping
{valhead:Boolean}
Value with two states, **true** or **false**
**Examples:**
* true
* false
{valhead:Size}
Size type, defined by 2 integers, width followed by height
size: width height
**Examples:**
* 10 20
* 30 10
{valhead:Rect}
Rect type, defined by 4 integers
rect: x y width height
**Examples:**
* 0 0 32 32
* 10 20 30 40
{valhead:Color}
{valhead:Image}
{valhead:Font}
## UIWidget
{taghead:rect Rect}
Defines widget's rect
**Examples:**
!!!plain
rect: 32 32 32 32
**See also:** {tag:pos}, {tag:size}
{taghead:size Size}
Defines size of a widget in pixels
**Examples:**
!!!plain
size: 32 32
{taghead:width Integer}
Defines width of a widget
{taghead:height Integer}
Defines height of a widget
{taghead:pos Point}
Defines absolute position of the widget relative to the window top left, this is generialy not used,
if you want to position relative to parent widget, use anchors and margins
**Examples:**
!!!plain
pos: 32 32
{taghead:x Integer}
Defines x absolute position
**See also:** {tag:pos}
{taghead:y Integer}
Defines y absolute position
**See also:** {tag:pos}
{taghead:color Color}
Foreground color, mostly used for coloring texts
**Examples:**
!!!plain
color: red
color: #ff0000
color: #ff000080
{taghead:background Color}
Same as {tag:background-color}
{taghead:background-color Color}
Defines background color
{taghead:background-rect Rect}
{taghead:background-offset Point}
{taghead:background-offset-x Integer}
{taghead:background-offset-y Integer}
{taghead:background-size Size}
{taghead:background-width Integer}
{taghead:background-height Integer}
{taghead:icon Image}
{taghead:icon-source Image}
{taghead:icon-color Color}
{taghead:icon-offset-x Integer}
{taghead:icon-offset-y Integer}
{taghead:icon-offset Point}
{taghead:icon-width Integer}
{taghead:icon-height Integer}
{taghead:icon-size Size}
{taghead:icon-rect Rect}
{taghead:opacity Float}
{taghead:enabled Boolean}
{taghead:visible Boolean}
{taghead:checked Boolean}
{taghead:dragable Boolean}
{taghead:on Boolean}
{taghead:focusable Boolean}
{taghead:phantom Boolean}
{taghead:fixed-size Boolean}
{taghead:clipping Boolean}
{taghead:border Integer}
{taghead:border-width Integer}
{taghead:border-width-top Integer}
{taghead:border-width-right Integer}
{taghead:border-width-bottom Integer}
{taghead:border-width-left Integer}
{taghead:border-color Color}
{taghead:border-color-top Color}
{taghead:border-color-right Color}
{taghead:border-color-bottom Color}
{taghead:border-color-left Color}
{taghead:margin-top Integer}
{taghead:margin-right Integer}
{taghead:margin-bottom Integer}
{taghead:margin-left Integer}
{taghead:margin Integer}
{taghead:padding-top Integer}
{taghead:padding-right Integer}
{taghead:padding-bottom Integer}
{taghead:padding-left Integer}
{taghead:padding Integer}
{taghead:layout Layout}
{taghead:image-source}
{taghead:image-offset-x Integer}
{taghead:image-offset-y Integer}
{taghead:image-offset Point}
{taghead:image-width Integer}
{taghead:image-height Integer}
{taghead:image-size Size}
{taghead:image-rect Rect}
{taghead:image-clip Rect}
{taghead:image-fixed-ratio Boolean}
{taghead:image-repeated Boolean}
{taghead:image-smooth Boolean}
{taghead:image-color Color}
{taghead:image-border-top Integer}
{taghead:image-border-right Integer}
{taghead:image-border-bottom Integer}
{taghead:image-border-left Integer}
{taghead:image-border Integer}
{taghead:text}
{taghead:text-align Align}
{taghead:text-offset Point}
{taghead:text-wrap Boolean}
{taghead:text-auto-resize Boolean}
{taghead:font Font}
## UITextEdit
{taghead:text-margin}
{taghead:always-active}
{taghead:shift-navigation}
{taghead:multiline}
{taghead:max-length}

@ -1,477 +0,0 @@
# @group Global functions
# Converts rect to string
# @return [Rect]
def torect(str); end
# Converts point to string
# @return [Point]
def topoint(str); end
# Converts color to string
# @return [Color]
def tocolor(str); end
# @return [Size]
def tosize(str); end
# @return [String]
def recttostring(rect); end
# @return [String]
def pointtostring(point); end
# @return [String]
def colortostring(color); end
# @return [String]
def sizetostring(size); end
# @endgroup
# All classes used by the engine is derived from this class
class LuaObject
# Return the number of references that this object have
# @return [Integer]
def getUseCount(); end
# Get the derived class name
# @return [String]
def getClassName(); end
# Return that hold all fields for this object
# @return [Table]
def getFieldsTable(); end
end
# Class that holds dispatcher events
class Event < LuaObject
# Cancel the event execution
# @return [Void]
def cancel(); end
# Force event execution, as an event can only be executed once,
# it will not be executed again in the next poll
# @return [Void]
def execute(); end
# Checks if the event is canceled
# @return [Boolean]
def isCanceled(); end
# Check if the event is executed
# @return [Boolean]
def isExecuted(); end
end
# Class that holds dispatcher scheduled events
class ScheduledEvent < Event
# Return ticks in milliseconds remaining to the event execution
# @return [Integer]
def reamaningTicks(); end
# Return ticks when this event will be executed
# @return [Integer]
def ticks(); end
end
# This is the base class for all UI elements
class UIWidget < LuaObject
# Creates a new UIWidget
# @return [UIWidget]
def self.create(); end
def addChild(); end
def insertChild(); end
def removeChild(); end
def focusChild(); end
def focusNextChild(); end
def focusPreviousChild(); end
def lowerChild(); end
def raiseChild(); end
def moveChildToIndex(); end
def lockChild(); end
def unlockChild(); end
def mergeStyle(); end
def applyStyle(); end
def addAnchor(); end
def removeAnchor(); end
def fill(); end
def centerIn(); end
def breakAnchors(); end
def updateParentLayout(); end
def updateLayout(); end
def lock(); end
def unlock(); end
def focus(); end
def lower(); end
def raise(); end
def grabMouse(); end
def ungrabMouse(); end
def grabKeyboard(); end
def ungrabKeyboard(); end
def bindRectToParent(); end
def destroy(); end
def destroyChildren(); end
def setId(); end
def setParent(); end
def setLayout(); end
def setRect(); end
def setStyle(); end
def setStyleFromNode(); end
def setEnabled(); end
def setVisible(); end
def setOn(); end
def setChecked(); end
def setFocusable(); end
def setPhantom(); end
def setDragable(); end
def setFixedSize(); end
def setClipping(); end
def setLastFocusReason(); end
def setAutoRepeatDelay(); end
def setVirtualOffset(); end
def isVisible(); end
def isChildLocked(); end
def hasChild(); end
def getChildIndex(); end
def getMarginRect(); end
def getClippingRect(); end
def getChildrenRect(); end
def getAnchoredLayout(); end
def getRootParent(); end
def getChildAfter(); end
def getChildBefore(); end
def getChildById(); end
def getChildByPos(); end
def getChildByIndex(); end
def recursiveGetChildById(); end
def recursiveGetChildByPos(); end
def recursiveGetChildrenByPos(); end
def backwardsGetWidgetById(); end
def asUIWidget(); end
def resize(); end
def move(); end
def hide(); end
def show(); end
def disable(); end
def enable(); end
def isActive(); end
def isEnabled(); end
def isDisabled(); end
def isFocused(); end
def isHovered(); end
def isPressed(); end
def isFirst(); end
def isMiddle(); end
def isLast(); end
def isAlternate(); end
def isChecked(); end
def isOn(); end
def isDragging(); end
def isHidden(); end
def isExplicitlyEnabled(); end
def isExplicitlyVisible(); end
def isFocusable(); end
def isPhantom(); end
def isDragable(); end
def isFixedSize(); end
def isClipping(); end
def isDestroyed(); end
def hasChildren(); end
def containsPoint(); end
def getId(); end
def getParent(); end
def getFocusedChild(); end
def getChildren(); end
def getFirstChild(); end
def getLastChild(); end
def getLayout(); end
def getStyle(); end
def getChildCount(); end
def getLastFocusReason(); end
def getAutoRepeatDelay(); end
def getVirtualOffset(); end
def getStyleName(); end
def getLastClickPosition(); end
def setX(); end
def setY(); end
def setWidth(); end
def setHeight(); end
def setSize(); end
def setPosition(); end
def setColor(); end
def setBackgroundColor(); end
def setBackgroundOffsetX(); end
def setBackgroundOffsetY(); end
def setBackgroundOffset(); end
def setBackgroundWidth(); end
def setBackgroundHeight(); end
def setBackgroundSize(); end
def setBackgroundRect(); end
def setIcon(); end
def setIconColor(); end
def setIconOffsetX(); end
def setIconOffsetY(); end
def setIconOffset(); end
def setIconWidth(); end
def setIconHeight(); end
def setIconSize(); end
def setIconRect(); end
def setBorderWidth(); end
def setBorderWidthTop(); end
def setBorderWidthRight(); end
def setBorderWidthBottom(); end
def setBorderWidthLeft(); end
def setBorderColor(); end
def setBorderColorTop(); end
def setBorderColorRight(); end
def setBorderColorBottom(); end
def setBorderColorLeft(); end
def setMargin(); end
def setMarginHorizontal(); end
def setMarginVertical(); end
def setMarginTop(); end
def setMarginRight(); end
def setMarginBottom(); end
def setMarginLeft(); end
def setPadding(); end
def setPaddingHorizontal(); end
def setPaddingVertical(); end
def setPaddingTop(); end
def setPaddingRight(); end
def setPaddingBottom(); end
def setPaddingLeft(); end
def setOpacity(); end
def getX(); end
def getY(); end
def getPosition(); end
def getWidth(); end
def getHeight(); end
def getSize(); end
def getRect(); end
def getColor(); end
def getBackgroundColor(); end
def getBackgroundOffsetX(); end
def getBackgroundOffsetY(); end
def getBackgroundOffset(); end
def getBackgroundWidth(); end
def getBackgroundHeight(); end
def getBackgroundSize(); end
def getBackgroundRect(); end
def getIconColor(); end
def getIconOffsetX(); end
def getIconOffsetY(); end
def getIconOffset(); end
def getIconWidth(); end
def getIconHeight(); end
def getIconSize(); end
def getIconRect(); end
def getBorderTopColor(); end
def getBorderRightColor(); end
def getBorderBottomColor(); end
def getBorderLeftColor(); end
def getBorderTopWidth(); end
def getBorderRightWidth(); end
def getBorderBottomWidth(); end
def getBorderLeftWidth(); end
def getMarginTop(); end
def getMarginRight(); end
def getMarginBottom(); end
def getMarginLeft(); end
def getPaddingTop(); end
def getPaddingRight(); end
def getPaddingBottom(); end
def getPaddingLeft(); end
def getOpacity(); end
def setImageSource(); end
def setImageClip(); end
def setImageOffsetX(); end
def setImageOffsetY(); end
def setImageOffset(); end
def setImageWidth(); end
def setImageHeight(); end
def setImageSize(); end
def setImageRect(); end
def setImageColor(); end
def setImageFixedRatio(); end
def setImageRepeated(); end
def setImageSmooth(); end
def setImageBorderTop(); end
def setImageBorderRight(); end
def setImageBorderBottom(); end
def setImageBorderLeft(); end
def setImageBorder(); end
def getImageClip(); end
def getImageOffsetX(); end
def getImageOffsetY(); end
def getImageOffset(); end
def getImageWidth(); end
def getImageHeight(); end
def getImageSize(); end
def getImageRect(); end
def getImageColor(); end
def isImageFixedRatio(); end
def isImageSmooth(); end
def getImageBorderTop(); end
def getImageBorderRight(); end
def getImageBorderBottom(); end
def getImageBorderLeft(); end
def resizeToText(); end
def clearText(); end
def setText(); end
def setTextAlign(); end
def setTextOffset(); end
def setTextWrap(); end
def setTextAutoResize(); end
def setFont(); end
def getText(); end
def getDrawText(); end
def getTextAlign(); end
def getTextOffset(); end
def getTextWrap(); end
def getFont(); end
def getTextSize(); end
# @group Class Events
# Triggered when a style is applied to the widget
# @param styleName Name of the style
# @param styleNode Table containing all style tags and values
# @return [Void]
def onStyleApply(styleName, styleNode); end
# Triggered when widget size or position has changed
# @param oldRect Table containing the old geometry rect
# @param newRect Table containing the new geometry rect
# @return [Void]
def onGeometryChange(oldRect, newRect); end
# Triggered when widget's layout updates its contents
# @return [Void]
def onLayoutUpdate(); end
# Triggered when widget focus state changes
# @param focused Boolean representing the focus state
# @param reason One of the constants: *ActiveFocusReason* *MouseFocusReason* *KeyboardFocusReason*
# @return [Void]
def onFocusChange(focused, reason); end
# Triggered when child focus changes
# @return [Void]
def onChildFocusChange(focusedChild, unfocusedChild, reason); end
# Triggered when mouse enter or leaves widget area
# @return [Void]
def onHoverChange(hovered); end
# Triggered when this widget dragging begin
# @return [Boolean]
def onDragEnter(mousePos); end
# Triggered when this widget dragging end
# @return [Boolean]
def onDragLeave(droppedWidget, mousePos); end
# Triggered when moving mouse while in dragging state
# @return [Boolean]
def onDragMove(mousePos, mouseMoved); end
# Triggered when leaving other widget dragging state while the mouse is over this widget
# @return [Boolean]
def onDrop(draggedWidget, mousePos); end
# @return [Boolean]
def onKeyText(keyText); end
# @return [Boolean]
def onKeyDown(keyCode, keyboardModifiers); end
# @return [Boolean]
def onKeyPress(keyCode, keyboardModifiers, autoRepeatTicks); end
# @return [Boolean]
def onKeyUp(keyCode, keyboardModifiers); end
# @return [Boolean]
def onMousePress(mousePos, utton); end
# @return [Boolean]
def onMouseRelease(mousePos, button); end
# @return [Boolean]
def onMouseMove(mousePos, mouseMoved); end
# @return [Boolean]
def onMouseWheel(mousePos, direction); end
# Triggered when clicking and releasing the mouse left button inside widget area
# @return [Boolean]
def onClick(mousePos); end
# Triggered when pressing mouse left button two times inside widget area
# @return [Boolean]
def onDoubleClick(mousePos); end
# @endgroup
end
class g_game
def self.login(); end
def self.logout(); end
def self.loginWorld(); end
def self.cancelLogin(); end
def self.forceLogout(); end
def self.safeLogout(); end
def self.walk(); end
def self.autoWalk(); end
def self.forceWalk(); end
def self.turn(); end
def self.stop(); end
def self.look(); end
def self.move(); end
def self.moveToParentContainer(); end
def self.rotate(); end
def self.use(); end
def self.useWith(); end
def self.useInventoryItem(); end
def self.useInventoryItemWith(); end
def self.open(); end
def self.openParent(); end
def self.close(); end
def self.refreshContainer(); end
def self.attack(); end
def self.cancelAttack(); end
def self.follow(); end
def self.cancelFollow(); end
def self.cancelAttackAndFollow(); end
def self.talk(); end
def self.talkChannel(); end
def self.talkPrivate(); end
def self.openPrivateChannel(); end
def self.requestChannels(); end
def self.joinChannel(); end
def self.leaveChannel(); end
def self.closeNpcChannel(); end
def self.openOwnChannel(); end
def self.inviteToOwnChannel(); end
def self.excludeFromOwnChannel(); end
def self.partyInvite(); end
def self.partyJoin(); end
def self.partyRevokeInvitation(); end
def self.partyPassLeadership(); end
def self.partyLeave(); end
def self.partyShareExperience(); end
def self.requestOutfit(); end
def self.changeOutfit(); end
def self.addVip(); end
def self.removeVip(); end
def self.setChaseMode(); end
def self.setFightMode(); end
def self.setSafeFight(); end
def self.getChaseMode(); end
def self.getFightMode(); end
def self.isSafeFight(); end
def self.inspectNpcTrade(); end
def self.buyItem(); end
def self.sellItem(); end
def self.closeNpcTrade(); end
def self.requestTrade(); end
def self.inspectTrade(); end
def self.acceptTrade(); end
def self.rejectTrade(); end
def self.reportBug(); end
def self.reportRuleVilation(); end
def self.debugReport(); end
def self.editText(); end
def self.editList(); end
def self.requestQuestLog(); end
def self.requestQuestLine(); end
def self.canPerformGameAction(); end
def self.canReportBugs(); end
def self.checkBotProtection(); end
def self.isOnline(); end
def self.isDead(); end
def self.isAttacking(); end
def self.isFollowing(); end
def self.getContainer(); end
def self.getContainers(); end
def self.getVips(); end
def self.getAttackingCreature(); end
def self.getFollowingCreature(); end
def self.getServerBeat(); end
def self.getLocalPlayer(); end
def self.getProtocolGame(); end
def self.getProtocolVersion(); end
def self.getWorldName(); end
def self.getGMActions(); end
end

@ -1,27 +0,0 @@
include YARD
include Templates
module MyTemplateHelper
def linkify(*args)
if args.first.is_a?(String)
case args.first
when /^taghead:(\S+)/
tag_name = $1
params = args[1]
return "<h3 class=\"note\" id=\"#{tag_name}\" toc-title=\"#{tag_name}\"><strong>#{tag_name}:</strong> #{params}</h3>"
when /^valhead:(\S+)/
tag_name = $1
return "<h3 class=\"note private\" id=\"#{tag_name}\" toc-title=\"#{tag_name}\"><strong>#{tag_name}</strong></h3>"
when /^tag:(\S+)/
tag_name = $1
return "<a href=\"##{tag_name}\">#{tag_name}</a>"
else
super
end
end
super
end
end
Template.extra_includes << MyTemplateHelper
Engine.register_template_path(File.dirname(__FILE__))

@ -4,7 +4,8 @@ function Client.reloadScripts()
g_modules.reloadModules() g_modules.reloadModules()
dofile '/otclientrc' dofile '/otclientrc'
local message = tr('All modules and scripts were reloaded.') local message = tr('All modules and scripts were reloaded.')
TextMessage.displayEventAdvance(message)
modules.game_textmessage.displayEventAdvance(message)
print(message) print(message)
end end

@ -137,7 +137,7 @@ function Options.setOption(key, value)
g_sounds.enableMusic(value) g_sounds.enableMusic(value)
elseif key == 'showLeftPanel' then elseif key == 'showLeftPanel' then
addEvent(function() addEvent(function()
GameInterface.getLeftPanel():setOn(value) modules.game_interface.getLeftPanel():setOn(value)
end) end)
elseif key == 'backgroundFrameRate' then elseif key == 'backgroundFrameRate' then
local text = value local text = value

@ -2,6 +2,7 @@
-- root widget -- root widget
rootWidget = g_ui.getRootWidget() rootWidget = g_ui.getRootWidget()
modules = package.loaded
-- G is used as a global table to save variables in memory between reloads -- G is used as a global table to save variables in memory between reloads
G = G or {} G = G or {}

@ -36,7 +36,17 @@ function quit()
g_app.quit() g_app.quit()
end end
function connect(object, signalsAndSlots, pushFront) function connect(object, arg1, arg2, arg3)
local signalsAndSlots
local pushFront
if type(arg1) == 'string' then
signalsAndSlots = { [arg1] = arg2 }
pushFront = arg3
else
signalsAndSlots = arg1
pushFront = arg2
end
for signal,slot in pairs(signalsAndSlots) do for signal,slot in pairs(signalsAndSlots) do
if not object[signal] then if not object[signal] then
local mt = getmetatable(object) local mt = getmetatable(object)
@ -150,6 +160,14 @@ local function module_loader(modname)
end end
table.insert(package.loaders, 1, module_loader) table.insert(package.loaders, 1, module_loader)
function import(table)
assert(type(table) == 'table')
local env = getfenv(2)
for k,v in pairs(table) do
env[k] = v
end
end
function export(what, key) function export(what, key)
if key ~= nil then if key ~= nil then
_G[key] = what _G[key] = what

@ -1,45 +1,41 @@
Battle = {}
--TODO --TODO
--onCreatureAppears onCreatureHealthChange onCreatureDisappears --onCreatureAppears onCreatureHealthChange onCreatureDisappears
--reloadable/disconnects --reloadable/disconnects
-- private variables battleWindow = nil
local battleWindow battleButton = nil
local battleButton battlePanel = nil
local battlePanel lastBattleButtonSwitched = nil
local lastBattleButtonSwitched checkCreaturesEvent = nil
local checkCreaturesEvent battleButtonsByCreaturesList = {}
local battleButtonsByCreaturesList = {}
local mouseWidget mouseWidget = nil
local hidePlayersButton hidePlayersButton = nil
local hideNPCsButton hideNPCsButton = nil
local hideMonstersButton hideMonstersButton = nil
local hideSkullsButton hideSkullsButton = nil
local hidePartyButton hidePartyButton = nil
local battleButtonColors = { BattleButtonColors = {
onIdle = {notHovered = '#888888', hovered = '#FFFFFF' }, onIdle = {notHovered = '#888888', hovered = '#FFFFFF' },
onTargeted = {notHovered = '#FF0000', hovered = '#FF8888' }, onTargeted = {notHovered = '#FF0000', hovered = '#FF8888' },
onFollowed = {notHovered = '#00FF00', hovered = '#88FF88' } onFollowed = {notHovered = '#00FF00', hovered = '#88FF88' }
} }
local lifeBarColors = {} --Must be sorted by percentAbose LifeBarColors = {} --Must be sorted by percentAbose
table.insert(lifeBarColors, {percentAbove = 92, color = '#00BC00' } ) table.insert(LifeBarColors, {percentAbove = 92, color = '#00BC00' } )
table.insert(lifeBarColors, {percentAbove = 60, color = '#50A150' } ) table.insert(LifeBarColors, {percentAbove = 60, color = '#50A150' } )
table.insert(lifeBarColors, {percentAbove = 30, color = '#A1A100' } ) table.insert(LifeBarColors, {percentAbove = 30, color = '#A1A100' } )
table.insert(lifeBarColors, {percentAbove = 8, color = '#3C2727' } ) table.insert(LifeBarColors, {percentAbove = 8, color = '#3C2727' } )
table.insert(lifeBarColors, {percentAbove = 3, color = '#3C0000' } ) table.insert(LifeBarColors, {percentAbove = 3, color = '#3C0000' } )
table.insert(lifeBarColors, {percentAbove = -1, color = '#4F0000' } ) table.insert(LifeBarColors, {percentAbove = -1, color = '#4F0000' } )
-- public functions function init()
function Battle.init() battleWindow = g_ui.loadUI('battle.otui', modules.game_interface.getRightPanel())
battleWindow = g_ui.loadUI('battle.otui', GameInterface.getRightPanel()) battleButton = TopMenu.addRightGameToggleButton('battleButton', tr('Battle') .. ' (Ctrl+B)', 'battle.png', toggle)
battleButton = TopMenu.addRightGameToggleButton('battleButton', tr('Battle') .. ' (Ctrl+B)', 'battle.png', Battle.toggle)
battleButton:setOn(true) battleButton:setOn(true)
g_keyboard.bindKeyDown('Ctrl+B', Battle.toggle) g_keyboard.bindKeyDown('Ctrl+B', toggle)
battlePanel = battleWindow:recursiveGetChildById('battlePanel') battlePanel = battleWindow:recursiveGetChildById('battlePanel')
@ -53,46 +49,32 @@ function Battle.init()
mouseWidget:setVisible(false) mouseWidget:setVisible(false)
mouseWidget:setFocusable(false) mouseWidget:setFocusable(false)
connect(Creature, { onSkullChange = Battle.checkCreatureSkull, connect(Creature, { onSkullChange = checkCreatureSkull,
onEmblemChange = Battle.checkCreatureEmblem } ) onEmblemChange = checkCreatureEmblem } )
connect(g_game, { onAttackingCreatureChange = Battle.onAttack, connect(g_game, { onAttackingCreatureChange = onAttack,
onFollowingCreatureChange = Battle.onFollow, onFollowingCreatureChange = onFollow,
onGameEnd = Battle.removeAllCreatures } ) onGameEnd = removeAllCreatures } )
addEvent(Battle.addAllCreatures) addEvent(addAllCreatures)
checkCreaturesEvent = scheduleEvent(Battle.checkCreatures, 200) checkCreaturesEvent = scheduleEvent(checkCreatures, 200)
end end
function Battle.terminate() function terminate()
g_keyboard.unbindKeyDown('Ctrl+B') g_keyboard.unbindKeyDown('Ctrl+B')
battlePanel = nil
lastBattleButtonTargeted = nil
lastBattleButtonFollowed = nil
battleButtonsByCreaturesList = {} battleButtonsByCreaturesList = {}
removeEvent(checkCreaturesEvent) removeEvent(checkCreaturesEvent)
hidePlayersButton = nil
hideNPCsButton = nil
hideMonstersButton = nil
hideSkullsButton = nil
hidePartyButton = nil
checkCreaturesEvent = nil
battleButton:destroy() battleButton:destroy()
battleButton = nil
battleWindow:destroy() battleWindow:destroy()
battleWindow = nil
mouseWidget:destroy() mouseWidget:destroy()
mouseWidget = nil
disconnect(Creature, { onSkullChange = Battle.checkCreatureSkull,
onEmblemChange = Battle.checkCreatureEmblem } )
disconnect(g_game, { onAttackingCreatureChange = Battle.onAttack } ) disconnect(Creature, { onSkullChange = checkCreatureSkull,
onEmblemChange = checkCreatureEmblem } )
Battle = nil disconnect(g_game, { onAttackingCreatureChange = onAttack } )
end end
function Battle.toggle() function toggle()
if battleButton:isOn() then if battleButton:isOn() then
battleWindow:close() battleWindow:close()
battleButton:setOn(false) battleButton:setOn(false)
@ -102,28 +84,28 @@ function Battle.toggle()
end end
end end
function Battle.onMiniWindowClose() function onMiniWindowClose()
battleButton:setOn(false) battleButton:setOn(false)
end end
function Battle.addAllCreatures() function addAllCreatures()
local spectators = {} local spectators = {}
local player = g_game.getLocalPlayer() local player = g_game.getLocalPlayer()
if player then if player then
creatures = g_map.getSpectators(player:getPosition(), false) creatures = g_map.getSpectators(player:getPosition(), false)
for i, creature in ipairs(creatures) do for i, creature in ipairs(creatures) do
if creature ~= player and Battle.doCreatureFitFilters(creature) then if creature ~= player and doCreatureFitFilters(creature) then
table.insert(spectators, creature) table.insert(spectators, creature)
end end
end end
end end
for i, v in pairs(spectators) do for i, v in pairs(spectators) do
Battle.addCreature(v) addCreature(v)
end end
end end
function Battle.doCreatureFitFilters(creature) function doCreatureFitFilters(creature)
local hidePlayers = hidePlayersButton:isChecked() local hidePlayers = hidePlayersButton:isChecked()
local hideNPCs = hideNPCsButton:isChecked() local hideNPCs = hideNPCsButton:isChecked()
local hideMonsters = hideMonstersButton:isChecked() local hideMonsters = hideMonstersButton:isChecked()
@ -145,7 +127,7 @@ function Battle.doCreatureFitFilters(creature)
return true return true
end end
function Battle.checkCreatures(forceRecheck) function checkCreatures(forceRecheck)
local player = g_game.getLocalPlayer() local player = g_game.getLocalPlayer()
if player then if player then
local spectators = {} local spectators = {}
@ -154,20 +136,20 @@ function Battle.checkCreatures(forceRecheck)
local creaturesAppeared = {} local creaturesAppeared = {}
creatures = g_map.getSpectators(player:getPosition(), false) creatures = g_map.getSpectators(player:getPosition(), false)
for i, creature in ipairs(creatures) do for i, creature in ipairs(creatures) do
if creature ~= player and Battle.doCreatureFitFilters(creature) then if creature ~= player and doCreatureFitFilters(creature) then
-- searching for creatures that appeared on battle list -- searching for creatures that appeared on battle list
local battleButton = battleButtonsByCreaturesList[creature:getId()] local battleButton = battleButtonsByCreaturesList[creature:getId()]
if battleButton == nil then if battleButton == nil then
table.insert(creaturesAppeared, creature) table.insert(creaturesAppeared, creature)
else else
Battle.setLifeBarPercent(battleButton, creature:getHealthPercent()) setLifeBarPercent(battleButton, creature:getHealthPercent())
end end
spectators[creature:getId()] = creature spectators[creature:getId()] = creature
end end
end end
for i, v in pairs(creaturesAppeared) do for i, v in pairs(creaturesAppeared) do
Battle.addCreature(v) addCreature(v)
end end
-- searching for creatures that disappeared from battle list -- searching for creatures that disappeared from battle list
@ -179,15 +161,15 @@ function Battle.checkCreatures(forceRecheck)
end end
for i, v in pairs(creaturesDisappeared) do for i, v in pairs(creaturesDisappeared) do
Battle.removeCreature(v) removeCreature(v)
end end
end end
if not forceRecheck then if not forceRecheck then
checkCreaturesEvent = scheduleEvent(Battle.checkCreatures, 500) checkCreaturesEvent = scheduleEvent(checkCreatures, 500)
end end
end end
function Battle.addCreature(creature) function addCreature(creature)
local creatureId = creature:getId() local creatureId = creature:getId()
if battleButtonsByCreaturesList[creatureId] == nil then if battleButtonsByCreaturesList[creatureId] == nil then
@ -205,16 +187,16 @@ function Battle.addCreature(creature)
labelWidget:setText(creature:getName()) labelWidget:setText(creature:getName())
creatureWidget:setCreature(creature) creatureWidget:setCreature(creature)
Battle.setLifeBarPercent(battleButton, creature:getHealthPercent()) setLifeBarPercent(battleButton, creature:getHealthPercent())
battleButtonsByCreaturesList[creatureId] = battleButton battleButtonsByCreaturesList[creatureId] = battleButton
Battle.checkCreatureSkull(battleButton.creature) checkCreatureSkull(battleButton.creature)
Battle.checkCreatureEmblem(battleButton.creature) checkCreatureEmblem(battleButton.creature)
end end
end end
function Battle.checkCreatureSkull(creature, skullId) function checkCreatureSkull(creature, skullId)
local battleButton = battleButtonsByCreaturesList[creature:getId()] local battleButton = battleButtonsByCreaturesList[creature:getId()]
if battleButton then if battleButton then
local skullWidget = battleButton:getChildById('skull') local skullWidget = battleButton:getChildById('skull')
@ -235,7 +217,7 @@ function Battle.checkCreatureSkull(creature, skullId)
end end
end end
function Battle.checkCreatureEmblem(creature, emblemId) function checkCreatureEmblem(creature, emblemId)
local battleButton = battleButtonsByCreaturesList[creature:getId()] local battleButton = battleButtonsByCreaturesList[creature:getId()]
if battleButton then if battleButton then
local emblemId = emblemId or creature:getEmblem() local emblemId = emblemId or creature:getEmblem()
@ -259,9 +241,9 @@ function Battle.checkCreatureEmblem(creature, emblemId)
end end
end end
function Battle.onMouseRelease(self, mousePosition, mouseButton) function onMouseRelease(self, mousePosition, mouseButton)
if mouseButton == MouseRightButton then if mouseButton == MouseRightButton then
GameInterface.createThingMenu(mousePosition, nil, nil, self.creature) modules.game_interface.createThingMenu(mousePosition, nil, nil, self.creature)
return true return true
elseif mouseButton == MouseLeftButton then elseif mouseButton == MouseLeftButton then
if g_keyboard.isShiftPressed() then if g_keyboard.isShiftPressed() then
@ -277,13 +259,13 @@ function Battle.onMouseRelease(self, mousePosition, mouseButton)
end end
end end
function Battle.removeAllCreatures() function removeAllCreatures()
for i, v in pairs(battleButtonsByCreaturesList) do for i, v in pairs(battleButtonsByCreaturesList) do
Battle.removeCreature(v.creature) removeCreature(v.creature)
end end
end end
function Battle.removeCreature(creature) function removeCreature(creature)
local creatureId = creature:getId() local creatureId = creature:getId()
if battleButtonsByCreaturesList[creatureId] ~= nil then if battleButtonsByCreaturesList[creatureId] ~= nil then
@ -297,12 +279,12 @@ function Battle.removeCreature(creature)
end end
end end
function Battle.setLifeBarPercent(battleButton, percent) function setLifeBarPercent(battleButton, percent)
local lifeBarWidget = battleButton:getChildById('lifeBar') local lifeBarWidget = battleButton:getChildById('lifeBar')
lifeBarWidget:setPercent(percent) lifeBarWidget:setPercent(percent)
local color local color
for i, v in pairs(lifeBarColors) do for i, v in pairs(LifeBarColors) do
if percent > v.percentAbove then if percent > v.percentAbove then
color = v.color color = v.color
break break
@ -312,37 +294,37 @@ function Battle.setLifeBarPercent(battleButton, percent)
lifeBarWidget:setBackgroundColor(color) lifeBarWidget:setBackgroundColor(color)
end end
function Battle.onbattleButtonHoverChange(widget, hovered) function onbattleButtonHoverChange(widget, hovered)
if widget.isBattleButton then if widget.isBattleButton then
widget.isHovered = hovered widget.isHovered = hovered
Battle.checkBattleButton(widget) checkBattleButton(widget)
end end
end end
function Battle.onAttack(creature) function onAttack(creature)
Battle.checkCreatures(true) --Force recheck checkCreatures(true) --Force recheck
local battleButton = creature and battleButtonsByCreaturesList[creature:getId()] or lastBattleButtonSwitched local battleButton = creature and battleButtonsByCreaturesList[creature:getId()] or lastBattleButtonSwitched
if battleButton then if battleButton then
battleButton.isTarget = creature and true or false battleButton.isTarget = creature and true or false
Battle.checkBattleButton(battleButton) checkBattleButton(battleButton)
end end
end end
function Battle.onFollow(creature) function onFollow(creature)
Battle.checkCreatures(true) --Force recheck checkCreatures(true) --Force recheck
local battleButton = creature and battleButtonsByCreaturesList[creature:getId()] or lastBattleButtonSwitched local battleButton = creature and battleButtonsByCreaturesList[creature:getId()] or lastBattleButtonSwitched
if battleButton then if battleButton then
battleButton.isFollowed = creature and true or false battleButton.isFollowed = creature and true or false
Battle.checkBattleButton(battleButton) checkBattleButton(battleButton)
end end
end end
function Battle.checkBattleButton(battleButton) function checkBattleButton(battleButton)
local color = battleButtonColors.onIdle local color = BattleButtonColors.onIdle
if battleButton.isTarget then if battleButton.isTarget then
color = battleButtonColors.onTargeted color = BattleButtonColors.onTargeted
elseif battleButton.isFollowed then elseif battleButton.isFollowed then
color = battleButtonColors.onFollowed color = BattleButtonColors.onFollowed
end end
color = battleButton.isHovered and color.hovered or color.notHovered color = battleButton.isHovered and color.hovered or color.notHovered
@ -363,7 +345,7 @@ function Battle.checkBattleButton(battleButton)
if lastBattleButtonSwitched and lastBattleButtonSwitched ~= battleButton then if lastBattleButtonSwitched and lastBattleButtonSwitched ~= battleButton then
lastBattleButtonSwitched.isTarget = false lastBattleButtonSwitched.isTarget = false
lastBattleButtonSwitched.isFollowed = false lastBattleButtonSwitched.isFollowed = false
Battle.checkBattleButton(lastBattleButtonSwitched) checkBattleButton(lastBattleButtonSwitched)
end end
lastBattleButtonSwitched = battleButton lastBattleButtonSwitched = battleButton
end end

@ -3,15 +3,7 @@ Module
description: Manage battle window description: Manage battle window
author: andrefaramir, BeniS author: andrefaramir, BeniS
website: www.otclient.info website: www.otclient.info
icon: battle.png sandboxed: true
scripts: [ battle.lua ]
dependencies: @onLoad: init()
- game_interface @onUnload: terminate()
@onLoad: |
dofile 'battle'
Battle.init()
@onUnload: |
Battle.terminate()

@ -41,7 +41,7 @@ MiniWindow
!text: tr('Battle') !text: tr('Battle')
height: 166 height: 166
icon: battle.png icon: battle.png
@onClose: Battle.onMiniWindowClose() @onClose: onMiniWindowClose()
&save: true &save: true
MiniWindowContents MiniWindowContents

@ -4,8 +4,8 @@ BattleButton
height: 20 height: 20
margin-top: 5 margin-top: 5
fixed-size: true fixed-size: true
&onHoverChange: Battle.onbattleButtonHoverChange &onHoverChange: onbattleButtonHoverChange
&onMouseRelease: Battle.onMouseRelease &onMouseRelease: onMouseRelease
&isBattleButton: true &isBattleButton: true
UICreature UICreature

@ -1,10 +1,9 @@
BugReport = {} HOTKEY = 'Ctrl+Z'
local bugReportWindow bugReportWindow = nil
local bugTextEdit bugTextEdit = nil
local HOTKEY = 'Ctrl+Z'
function BugReport.init() function init()
g_ui.importStyle('bugreport.otui') g_ui.importStyle('bugreport.otui')
bugReportWindow = g_ui.createWidget('BugReportWindow', rootWidget) bugReportWindow = g_ui.createWidget('BugReportWindow', rootWidget)
@ -12,23 +11,21 @@ function BugReport.init()
bugTextEdit = bugReportWindow:getChildById('bugTextEdit') bugTextEdit = bugReportWindow:getChildById('bugTextEdit')
g_keyboard.bindKeyDown(HOTKEY, BugReport.show) g_keyboard.bindKeyDown(HOTKEY, show)
end end
function BugReport.terminate() function terminate()
g_keyboard.unbindKeyDown(HOTKEY) g_keyboard.unbindKeyDown(HOTKEY)
bugReportWindow:destroy() bugReportWindow:destroy()
bugReportWindow = nil
bugTextEdit = nil
end end
function BugReport.doReport() function doReport()
g_game.reportBug(bugTextEdit:getText()) g_game.reportBug(bugTextEdit:getText())
bugReportWindow:hide() bugReportWindow:hide()
TextMessage.displayEventAdvance(tr('Bug report sent.')) modules.game_textmessage.displayEventAdvance(tr('Bug report sent.'))
end end
function BugReport.show() function show()
bugTextEdit:setText('') bugTextEdit:setText('')
bugReportWindow:show() bugReportWindow:show()
bugReportWindow:raise() bugReportWindow:raise()

@ -3,13 +3,7 @@ Module
description: Bug report interface (Ctrl+Z) description: Bug report interface (Ctrl+Z)
author: edubart author: edubart
website: www.otclient.info website: www.otclient.info
scripts: [ bugreport.lua ]
dependencies: sandboxed: true
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'bugreport'
BugReport.init()
@onUnload: |
BugReport.terminate()

@ -28,7 +28,7 @@ BugReportWindow < MainWindow
anchors.right: cancelButton.left anchors.right: cancelButton.left
margin-right: 10 margin-right: 10
width: 80 width: 80
&onClick: BugReport.doReport &onClick: doReport
Button Button
id: cancelButton id: cancelButton

@ -1,49 +1,16 @@
CombatControls = {} combatControlsButton = nil
combatControlsWindow = nil
-- private variables fightOffensiveBox = nil
local combatControlsButton fightBalancedBox = nil
local combatControlsWindow fightDefensiveBox = nil
local fightOffensiveBox chaseModeButton = nil
local fightBalancedBox safeFightButton = nil
local fightDefensiveBox fightModeRadioGroup = nil
local chaseModeButton
local safeFightButton function init()
local fightModeRadioGroup combatControlsButton = TopMenu.addRightGameToggleButton('combatControlsButton', tr('Combat Controls'), 'combatcontrols.png', toggle)
-- private functions
local function onSetFightMode(self, selectedFightButton)
if selectedFightButton == nil then return end
local buttonId = selectedFightButton:getId()
local fightMode
if buttonId == 'fightOffensiveBox' then
fightMode = FightOffensive
elseif buttonId == 'fightBalancedBox' then
fightMode = FightBalanced
else
fightMode = FightDefensive
end
g_game.setFightMode(fightMode)
end
local function onSetChaseMode(self, checked)
local chaseMode
if checked then
chaseMode = ChaseOpponent
else
chaseMode = DontChase
end
g_game.setChaseMode(chaseMode)
end
local function onSetSafeFight(self, checked)
g_game.setSafeFight(not checked)
end
-- public functions
function CombatControls.init()
combatControlsButton = TopMenu.addRightGameToggleButton('combatControlsButton', tr('Combat Controls'), 'combatcontrols.png', CombatControls.toggle)
combatControlsButton:setOn(true) combatControlsButton:setOn(true)
combatControlsWindow = g_ui.loadUI('combatcontrols.otui', GameInterface.getRightPanel()) combatControlsWindow = g_ui.loadUI('combatcontrols.otui', modules.game_interface.getRightPanel())
combatControlsWindow:disableResize() combatControlsWindow:disableResize()
fightOffensiveBox = combatControlsWindow:recursiveGetChildById('fightOffensiveBox') fightOffensiveBox = combatControlsWindow:recursiveGetChildById('fightOffensiveBox')
@ -61,52 +28,39 @@ function CombatControls.init()
connect(chaseModeButton, { onCheckChange = onSetChaseMode }) connect(chaseModeButton, { onCheckChange = onSetChaseMode })
connect(safeFightButton, { onCheckChange = onSetSafeFight }) connect(safeFightButton, { onCheckChange = onSetSafeFight })
connect(g_game, { connect(g_game, {
onGameStart = CombatControls.online, onGameStart = online,
onGameEnd = CombatControls.offline, onGameEnd = offline,
onFightModeChange = CombatControls.update, onFightModeChange = update,
onChaseModeChange = CombatControls.update, onChaseModeChange = update,
onSafeFightChange = CombatControls.update, onSafeFightChange = update,
onWalk = CombatControls.check onWalk = check
}) })
if g_game.isOnline() then if g_game.isOnline() then
CombatControls.online() online()
end end
end end
function CombatControls.terminate() function terminate()
if g_game.isOnline() then if g_game.isOnline() then
CombatControls.offline() offline()
end end
fightModeRadioGroup:destroy() fightModeRadioGroup:destroy()
fightModeRadioGroup = nil
fightOffensiveBox = nil
fightBalancedBox = nil
fightDefensiveBox = nil
chaseModeButton = nil
safeFightButton = nil
combatControlsButton:destroy() combatControlsButton:destroy()
combatControlsButton = nil
combatControlsWindow:destroy() combatControlsWindow:destroy()
combatControlsWindow = nil
disconnect(g_game, { disconnect(g_game, {
onGameStart = CombatControls.online, onGameStart = online,
onGameEnd = CombatControls.offline, onGameEnd = offline,
onFightModeChange = CombatControls.update, onFightModeChange = update,
onChaseModeChange = CombatControls.update, onChaseModeChange = update,
onSafeFightChange = CombatControls.update, onSafeFightChange = update,
onWalk = CombatControls.check onWalk = check
}) })
CombatControls = nil
end end
function CombatControls.update() function update()
local fightMode = g_game.getFightMode() local fightMode = g_game.getFightMode()
if fightMode == FightOffensive then if fightMode == FightOffensive then
fightModeRadioGroup:selectWidget(fightOffensiveBox) fightModeRadioGroup:selectWidget(fightOffensiveBox)
@ -123,7 +77,7 @@ function CombatControls.update()
safeFightButton:setChecked(not safeFight) safeFightButton:setChecked(not safeFight)
end end
function CombatControls.check() function check()
if(Options.getOption('autoChaseOverride')) then if(Options.getOption('autoChaseOverride')) then
if(g_game.isAttacking() and g_game.getChaseMode() == ChaseOpponent) then if(g_game.isAttacking() and g_game.getChaseMode() == ChaseOpponent) then
g_game.setChaseMode(DontChase) g_game.setChaseMode(DontChase)
@ -131,7 +85,7 @@ function CombatControls.check()
end end
end end
function CombatControls.online() function online()
local player = g_game.getLocalPlayer() local player = g_game.getLocalPlayer()
if(player) then if(player) then
local char = player:getName() local char = player:getName()
@ -148,10 +102,10 @@ function CombatControls.online()
end end
combatControlsWindow:setVisible(combatControlsButton:isOn()) combatControlsWindow:setVisible(combatControlsButton:isOn())
CombatControls.update() update()
end end
function CombatControls.offline() function offline()
local lastCombatControls = g_settings.getNode('LastCombatControls') local lastCombatControls = g_settings.getNode('LastCombatControls')
if(not lastCombatControls) then if(not lastCombatControls) then
lastCombatControls = {} lastCombatControls = {}
@ -171,7 +125,7 @@ function CombatControls.offline()
end end
end end
function CombatControls.toggle() function toggle()
if combatControlsButton:isOn() then if combatControlsButton:isOn() then
combatControlsWindow:close() combatControlsWindow:close()
combatControlsButton:setOn(false) combatControlsButton:setOn(false)
@ -181,6 +135,34 @@ function CombatControls.toggle()
end end
end end
function CombatControls.onMiniWindowClose() function onMiniWindowClose()
combatControlsButton:setOn(false) combatControlsButton:setOn(false)
end end
function onSetFightMode(self, selectedFightButton)
if selectedFightButton == nil then return end
local buttonId = selectedFightButton:getId()
local fightMode
if buttonId == 'fightOffensiveBox' then
fightMode = FightOffensive
elseif buttonId == 'fightBalancedBox' then
fightMode = FightBalanced
else
fightMode = FightDefensive
end
g_game.setFightMode(fightMode)
end
function onSetChaseMode(self, checked)
local chaseMode
if checked then
chaseMode = ChaseOpponent
else
chaseMode = DontChase
end
g_game.setChaseMode(chaseMode)
end
function onSetSafeFight(self, checked)
g_game.setSafeFight(not checked)
end

@ -3,13 +3,7 @@ Module
description: Combat controls window description: Combat controls window
author: edubart, BeniS author: edubart, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ combatcontrols.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'combatcontrols'
CombatControls.init()
@onUnload: |
CombatControls.terminate()

@ -1,7 +1,4 @@
Console = {} SpeakTypesSettings = {
-- private variables
local SpeakTypesSettings = {
say = { speakType = SpeakSay, color = '#FFFF00' }, say = { speakType = SpeakSay, color = '#FFFF00' },
whisper = { speakType = SpeakWhisper, color = '#FFFF00' }, whisper = { speakType = SpeakWhisper, color = '#FFFF00' },
yell = { speakType = SpeakYell, color = '#FFFF00' }, yell = { speakType = SpeakYell, color = '#FFFF00' },
@ -19,7 +16,7 @@ local SpeakTypesSettings = {
monsterYell = { speakType = SpeakMonsterYell, color = '#FE6500', hideInConsole = true}, monsterYell = { speakType = SpeakMonsterYell, color = '#FE6500', hideInConsole = true},
} }
local SpeakTypes = { SpeakTypes = {
[SpeakSay] = SpeakTypesSettings.say, [SpeakSay] = SpeakTypesSettings.say,
[SpeakWhisper] = SpeakTypesSettings.whisper, [SpeakWhisper] = SpeakTypesSettings.whisper,
[SpeakYell] = SpeakTypesSettings.yell, [SpeakYell] = SpeakTypesSettings.yell,
@ -36,235 +33,29 @@ local SpeakTypes = {
[SpeakMonsterYell] = SpeakTypesSettings.monsterYell, [SpeakMonsterYell] = SpeakTypesSettings.monsterYell,
} }
local SayModes = { SayModes = {
[1] = { speakTypeDesc = 'whisper', icon = 'icons/whisper.png' }, [1] = { speakTypeDesc = 'whisper', icon = 'icons/whisper.png' },
[2] = { speakTypeDesc = 'say', icon = 'icons/say.png' }, [2] = { speakTypeDesc = 'say', icon = 'icons/say.png' },
[3] = { speakTypeDesc = 'yell', icon = 'icons/yell.png' } [3] = { speakTypeDesc = 'yell', icon = 'icons/yell.png' }
} }
local MAX_HISTORY = 1000 MAX_HISTORY = 1000
local MAX_LINES = 100 MAX_LINES = 100
local HELP_CHANNEL = 9 HELP_CHANNEL = 9
local consolePanel
local consoleContentPanel
local consoleTabBar
local consoleTextEdit
local channels
local channelsWindow
local ownPrivateName
local messageHistory = {}
local currentMessageIndex = 0
local ignoreNpcMessages = false
-- private functions
local function navigateMessageHistory(step)
local numCommands = #messageHistory
if numCommands > 0 then
currentMessageIndex = math.min(math.max(currentMessageIndex + step, 0), numCommands)
if currentMessageIndex > 0 then
local command = messageHistory[numCommands - currentMessageIndex + 1]
consoleTextEdit:setText(command)
else
consoleTextEdit:clearText()
end
end
end
function applyMessagePrefixies(name, level, message)
if name then
if Options.getOption('showLevelsInConsole') and level > 0 then
message = name .. ' [' .. level .. ']: ' .. message
else
message = name .. ': ' .. message
end
end
return message
end
-- hooked events
local function onCreatureSpeak(name, level, speaktype, message, channelId, creaturePos)
if ignoreNpcMessages and speaktype == SpeakPrivateNpcToPlayer then return end
local defaultMessage = speaktype < 3 and true or false
speaktype = SpeakTypes[speaktype]
if speaktype.hideInConsole then return end
local composedMessage = applyMessagePrefixies(name, level, message)
if speaktype.private then
Console.addPrivateText(composedMessage, speaktype, name, false, name)
if Options.getOption('showPrivateMessagesOnScreen') then
if(speaktype.speakType ~= SpeakPrivateNpcToPlayer) then
TextMessage.displayPrivate(name .. ':\n' .. message)
end
end
else
local channel = tr('Default')
if not defaultMessage then
channel = channels[channelId]
end
if channel then
Console.addText(composedMessage, speaktype, channel, name)
elseif channelId ~= 0 then
-- server sent a message on a channel that is not open
pwarning('message in channel id ' .. channelId .. ' which is unknown, this is a server bug, relogin if you want to see messages in this channel')
end
end
end
local function onOpenChannel(channelId, channelName)
Console.addChannel(channelName, channelId)
end
local function onOpenPrivateChannel(receiver)
Console.addPrivateChannel(receiver)
end
local function onOpenOwnPrivateChannel(channelId, channelName)
local privateTab = Console.getTab(channelName)
if privateTab == nil then
Console.addChannel(channelName, channelId)
end
ownPrivateName = channelName
end
local function onCloseChannel(channelId)
local channel = channels[channelId]
if channel then
local tab = Console.getTab(channel)
if tab then
consoleTabBar:removeTab(tab)
end
for k, v in pairs(channels) do
if (k == tab.channelId) then channels[k] = nil end
end
end
end
local function doChannelListSubmit() consolePanel = nil
local channelListPanel = channelsWindow:getChildById('channelList') consoleContentPanel = nil
local openPrivateChannelWith = channelsWindow:getChildById('openPrivateChannelWith'):getText() consoleTabBar = nil
if openPrivateChannelWith ~= '' then consoleTextEdit = nil
g_game.openPrivateChannel(openPrivateChannelWith) channels = nil
else channelsWindow = nil
local selectedChannelLabel = channelListPanel:getFocusedChild() ownPrivateName = nil
if not selectedChannelLabel then return end messageHistory = {}
if selectedChannelLabel.channelId == 0xFFFF then currentMessageIndex = 0
g_game.openOwnChannel() ignoreNpcMessages = false
else
g_game.joinChannel(selectedChannelLabel.channelId)
end
end
channelsWindow:destroy()
end
local function onChannelList(channelList) function init()
if channelsWindow then channelsWindow:destroy() end
channelsWindow = g_ui.displayUI('channelswindow.otui')
local channelListPanel = channelsWindow:getChildById('channelList')
channelsWindow.onEnter = doChannelListSubmit
channelsWindow.onDestroy = function() channelsWindow = nil end
g_keyboard.bindKeyPress('Down', function() channelListPanel:focusNextChild(KeyboardFocusReason) end, channelsWindow)
g_keyboard.bindKeyPress('Up', function() channelListPanel:focusPreviousChild(KeyboardFocusReason) end, channelsWindow)
for k,v in pairs(channelList) do
local channelId = v[1]
local channelName = v[2]
if #channelName > 0 then
local label = g_ui.createWidget('ChannelListLabel', channelListPanel)
label.channelId = channelId
label:setText(channelName)
label:setPhantom(false)
label.onDoubleClick = doChannelListSubmit
end
end
end
local function onGameStart()
-- open last channels
local player = g_game.getLocalPlayer()
if(player) then
local char = player:getName()
local lastChannelsOpen = g_settings.getNode('LastChannelsOpen')
if(not table.empty(lastChannelsOpen) and lastChannelsOpen[char]) then
for channelName, channelId in ipairs(lastChannelsOpen[char]) do
channelId = tonumber(channelId)
if channelId ~= 0 then
if not table.find(channels, channelId) then
g_game.joinChannel(channelId)
end
end
end
end
end
local tab = Console.getTab(tr('Default'))
if tab then
--[[
Known Issue: The server is calling to open channels after
onGameStart is executed causing it to focus the last tab opened.
Fix: Don't save channels to the settings that are opened by the server.
]]
addEvent(function() consoleTabBar:selectTab(tab) end, true)
end
end
function Console.onTabChange(tabBar, tab)
if tab:getText() == tr('Default') or tab:getText() == tr('Server Log') then
consolePanel:getChildById('closeChannelButton'):disable()
else
consolePanel:getChildById('closeChannelButton'):enable()
end
end
function Console.clear()
local lastChannelsOpen = {}
local player = g_game.getLocalPlayer()
if(player) then
local char = player:getName()
lastChannelsOpen[char] = {}
for channelId, channelName in pairs(channels) do
table.insert(lastChannelsOpen[char], channelId)
end
end
-- save last open channels
g_settings.setNode('LastChannelsOpen', lastChannelsOpen)
for _, channelName in pairs(channels) do
local tab = consoleTabBar:getTab(channelName)
consoleTabBar:removeTab(tab)
end
channels = {}
consoleTabBar:getTab(tr('Default')).tabPanel:getChildById('consoleBuffer'):destroyChildren()
consoleTabBar:getTab(tr('Server Log')).tabPanel:getChildById('consoleBuffer'):destroyChildren()
local npcTab = consoleTabBar:getTab('NPCs')
if npcTab then
consoleTabBar:removeTab(npcTab)
end
consoleTextEdit:clearText()
if channelsWindow then
channelsWindow:destroy()
channelsWindow = nil
end
end
-- public functions
function Console.init()
connect(g_game, { onCreatureSpeak = onCreatureSpeak, connect(g_game, { onCreatureSpeak = onCreatureSpeak,
onChannelList = onChannelList, onChannelList = onChannelList,
onOpenChannel = onOpenChannel, onOpenChannel = onOpenChannel,
@ -272,37 +63,37 @@ function Console.init()
onOpenOwnPrivateChannel = onOpenOwnPrivateChannel, onOpenOwnPrivateChannel = onOpenOwnPrivateChannel,
onCloseChannel = onCloseChannel, onCloseChannel = onCloseChannel,
onGameStart = onGameStart, onGameStart = onGameStart,
onGameEnd = Console.clear }) onGameEnd = clear })
consolePanel = g_ui.loadUI('console.otui', GameInterface.getBottomPanel()) consolePanel = g_ui.loadUI('console.otui', modules.game_interface.getBottomPanel())
consoleTextEdit = consolePanel:getChildById('consoleTextEdit') consoleTextEdit = consolePanel:getChildById('consoleTextEdit')
consoleContentPanel = consolePanel:getChildById('consoleContentPanel') consoleContentPanel = consolePanel:getChildById('consoleContentPanel')
consoleTabBar = consolePanel:getChildById('consoleTabBar') consoleTabBar = consolePanel:getChildById('consoleTabBar')
consoleTabBar:setContentWidget(consoleContentPanel) consoleTabBar:setContentWidget(consoleContentPanel)
channels = {} channels = {}
Console.addTab(tr('Default'), true) addTab(tr('Default'), true)
Console.addTab(tr('Server Log'), false) addTab(tr('Server Log'), false)
g_keyboard.bindKeyPress('Shift+Up', function() navigateMessageHistory(1) end, consolePanel) g_keyboard.bindKeyPress('Shift+Up', function() navigateMessageHistory(1) end, consolePanel)
g_keyboard.bindKeyPress('Shift+Down', function() navigateMessageHistory(-1) end, consolePanel) g_keyboard.bindKeyPress('Shift+Down', function() navigateMessageHistory(-1) end, consolePanel)
g_keyboard.bindKeyPress('Tab', function() consoleTabBar:selectNextTab() end, consolePanel) g_keyboard.bindKeyPress('Tab', function() consoleTabBar:selectNextTab() end, consolePanel)
g_keyboard.bindKeyPress('Shift+Tab', function() consoleTabBar:selectPrevTab() end, consolePanel) g_keyboard.bindKeyPress('Shift+Tab', function() consoleTabBar:selectPrevTab() end, consolePanel)
g_keyboard.bindKeyDown('Enter', Console.sendCurrentMessage, consolePanel) g_keyboard.bindKeyDown('Enter', sendCurrentMessage, consolePanel)
g_keyboard.bindKeyPress('Ctrl+A', function() consoleTextEdit:clearText() end, consolePanel) g_keyboard.bindKeyPress('Ctrl+A', function() consoleTextEdit:clearText() end, consolePanel)
-- apply buttom functions after loaded -- apply buttom functions after loaded
consolePanel:getChildById('nextChannelButton').onClick = function() consoleTabBar:selectNextTab() end consolePanel:getChildById('nextChannelButton').onClick = function() consoleTabBar:selectNextTab() end
consolePanel:getChildById('prevChannelButton').onClick = function() consoleTabBar:selectPrevTab() end consolePanel:getChildById('prevChannelButton').onClick = function() consoleTabBar:selectPrevTab() end
consoleTabBar.onTabChange = Console.onTabChange consoleTabBar.onTabChange = onTabChange
-- tibia like hotkeys -- tibia like hotkeys
g_keyboard.bindKeyDown('Ctrl+O', g_game.requestChannels) g_keyboard.bindKeyDown('Ctrl+O', g_game.requestChannels)
g_keyboard.bindKeyDown('Ctrl+E', Console.removeCurrentTab) g_keyboard.bindKeyDown('Ctrl+E', removeCurrentTab)
g_keyboard.bindKeyDown('Ctrl+H', Console.openHelp) g_keyboard.bindKeyDown('Ctrl+H', openHelp)
end end
function Console.terminate() function terminate()
disconnect(g_game, { onCreatureSpeak = onCreatureSpeak, disconnect(g_game, { onCreatureSpeak = onCreatureSpeak,
onChannelList = onChannelList, onChannelList = onChannelList,
onOpenChannel = onOpenChannel, onOpenChannel = onOpenChannel,
@ -310,7 +101,7 @@ function Console.terminate()
onOpenOwnPrivateChannel = onOpenPrivateChannel, onOpenOwnPrivateChannel = onOpenPrivateChannel,
onCloseChannel = onCloseChannel, onCloseChannel = onCloseChannel,
onGameStart = onGameStart, onGameStart = onGameStart,
onGameEnd = Console.clear }) onGameEnd = clear })
for channelid, channelname in pairs(channels) do for channelid, channelname in pairs(channels) do
if tonumber(channelid) and tonumber(channelid) ~= 0 then if tonumber(channelid) and tonumber(channelid) ~= 0 then
@ -339,16 +130,63 @@ function Console.terminate()
Console = nil Console = nil
end end
function Console.setTextEditText(text) function onTabChange(tabBar, tab)
if tab:getText() == tr('Default') or tab:getText() == tr('Server Log') then
consolePanel:getChildById('closeChannelButton'):disable()
else
consolePanel:getChildById('closeChannelButton'):enable()
end
end
function clear()
local lastChannelsOpen = {}
local player = g_game.getLocalPlayer()
if(player) then
local char = player:getName()
lastChannelsOpen[char] = {}
for channelId, channelName in pairs(channels) do
table.insert(lastChannelsOpen[char], channelId)
end
end
-- save last open channels
g_settings.setNode('LastChannelsOpen', lastChannelsOpen)
for _, channelName in pairs(channels) do
local tab = consoleTabBar:getTab(channelName)
consoleTabBar:removeTab(tab)
end
channels = {}
consoleTabBar:getTab(tr('Default')).tabPanel:getChildById('consoleBuffer'):destroyChildren()
consoleTabBar:getTab(tr('Server Log')).tabPanel:getChildById('consoleBuffer'):destroyChildren()
local npcTab = consoleTabBar:getTab('NPCs')
if npcTab then
consoleTabBar:removeTab(npcTab)
end
consoleTextEdit:clearText()
if channelsWindow then
channelsWindow:destroy()
channelsWindow = nil
end
end
function setTextEditText(text)
consoleTextEdit:setText(text) consoleTextEdit:setText(text)
end end
function Console.openHelp() function openHelp()
g_game.joinChannel(HELP_CHANNEL) g_game.joinChannel(HELP_CHANNEL)
end end
function Console.addTab(name, focus) function addTab(name, focus)
local tab = Console.getTab(name) local tab = getTab(name)
if(tab) then -- is channel already open if(tab) then -- is channel already open
if(not focus) then focus = true end if(not focus) then focus = true end
else else
@ -362,7 +200,7 @@ function Console.addTab(name, focus)
return tab return tab
end end
function Console.removeCurrentTab() function removeCurrentTab()
local tab = consoleTabBar:getCurrentTab() local tab = consoleTabBar:getCurrentTab()
if tab:getText() == tr('Default') or tab:getText() == tr('Server Log') then return end if tab:getText() == tr('Default') or tab:getText() == tr('Server Log') then return end
@ -379,56 +217,56 @@ function Console.removeCurrentTab()
consoleTabBar:removeTab(tab) consoleTabBar:removeTab(tab)
end end
function Console.getTab(name) function getTab(name)
return consoleTabBar:getTab(name) return consoleTabBar:getTab(name)
end end
function Console.getCurrentTab() function getCurrentTab()
return consoleTabBar:getCurrentTab() return consoleTabBar:getCurrentTab()
end end
function Console.addChannel(name, id) function addChannel(name, id)
channels[id] = name channels[id] = name
local tab = Console.addTab(name, true) local tab = addTab(name, true)
tab.channelId = id tab.channelId = id
return tab return tab
end end
function Console.addPrivateChannel(receiver) function addPrivateChannel(receiver)
channels[receiver] = receiver channels[receiver] = receiver
return Console.addTab(receiver, true) return addTab(receiver, true)
end end
function Console.addPrivateText(text, speaktype, name, isPrivateCommand, creatureName) function addPrivateText(text, speaktype, name, isPrivateCommand, creatureName)
local focus = false local focus = false
if speaktype.speakType == SpeakPrivateNpcToPlayer then if speaktype.speakType == SpeakPrivateNpcToPlayer then
name = 'NPCs' name = 'NPCs'
focus = true focus = true
end end
local privateTab = Console.getTab(name) local privateTab = getTab(name)
if privateTab == nil then if privateTab == nil then
if (Options.getOption('showPrivateMessagesInConsole') and not focus) or (isPrivateCommand and not privateTab) then if (Options.getOption('showPrivateMessagesInConsole') and not focus) or (isPrivateCommand and not privateTab) then
privateTab = Console.getTab(tr('Default')) privateTab = getTab(tr('Default'))
else else
privateTab = Console.addTab(name, focus) privateTab = addTab(name, focus)
channels[name] = name channels[name] = name
end end
privateTab.npcChat = speaktype.npcChat privateTab.npcChat = speaktype.npcChat
elseif focus then elseif focus then
consoleTabBar:selectTab(privateTab) consoleTabBar:selectTab(privateTab)
end end
Console.addTabText(text, speaktype, privateTab, creatureName) addTabText(text, speaktype, privateTab, creatureName)
end end
function Console.addText(text, speaktype, tabName, creatureName) function addText(text, speaktype, tabName, creatureName)
local tab = Console.getTab(tabName) local tab = getTab(tabName)
if tab ~= nil then if tab ~= nil then
Console.addTabText(text, speaktype, tab, creatureName) addTabText(text, speaktype, tab, creatureName)
end end
end end
function Console.addTabText(text, speaktype, tab, creatureName) function addTabText(text, speaktype, tab, creatureName)
if Options.getOption('showTimestampsInConsole') then if Options.getOption('showTimestampsInConsole') then
text = os.date('%H:%M') .. ' ' .. text text = os.date('%H:%M') .. ' ' .. text
end end
@ -441,14 +279,14 @@ function Console.addTabText(text, speaktype, tab, creatureName)
label:setColor(speaktype.color) label:setColor(speaktype.color)
consoleTabBar:blinkTab(tab) consoleTabBar:blinkTab(tab)
label.onMouseRelease = function (self, mousePos, mouseButton) Console.popupMenu(mousePos, mouseButton, creatureName, text) end label.onMouseRelease = function (self, mousePos, mouseButton) popupMenu(mousePos, mouseButton, creatureName, text) end
if consoleBuffer:getChildCount() > MAX_LINES then if consoleBuffer:getChildCount() > MAX_LINES then
consoleBuffer:getFirstChild():destroy() consoleBuffer:getFirstChild():destroy()
end end
end end
function Console.popupMenu(mousePos, mouseButton, creatureName, text) function popupMenu(mousePos, mouseButton, creatureName, text)
if mouseButton == MouseRightButton then if mouseButton == MouseRightButton then
local menu = g_ui.createWidget('PopupMenu') local menu = g_ui.createWidget('PopupMenu')
if creatureName then if creatureName then
@ -478,13 +316,13 @@ function Console.popupMenu(mousePos, mouseButton, creatureName, text)
end end
end end
function Console.sendCurrentMessage() function sendCurrentMessage()
local message = consoleTextEdit:getText() local message = consoleTextEdit:getText()
if #message == 0 then return end if #message == 0 then return end
consoleTextEdit:clearText() consoleTextEdit:clearText()
-- get current channel -- get current channel
local tab = Console.getCurrentTab() local tab = getCurrentTab()
-- handling chat commands -- handling chat commands
local originalMessage = message local originalMessage = message
@ -527,7 +365,7 @@ function Console.sendCurrentMessage()
-- when talking on server log, the message goes to default channel -- when talking on server log, the message goes to default channel
local name = tab:getText() local name = tab:getText()
if name == tr('Server Log') then if name == tr('Server Log') then
tab = Console.getTab(tr('Default')) tab = getTab(tr('Default'))
name = tr('Default') name = tr('Default')
end end
@ -535,7 +373,7 @@ function Console.sendCurrentMessage()
if (tab.channelId or name == tr('Default')) and not chatCommandPrivateReady then if (tab.channelId or name == tr('Default')) and not chatCommandPrivateReady then
if name == tr('Default') then if name == tr('Default') then
speaktypedesc = chatCommandSayMode or SayModes[consolePanel:getChildById('sayModeButton').sayMode].speakTypeDesc speaktypedesc = chatCommandSayMode or SayModes[consolePanel:getChildById('sayModeButton').sayMode].speakTypeDesc
if speaktypedesc ~= 'say' then Console.sayModeChange(2) end -- head back to say mode if speaktypedesc ~= 'say' then sayModeChange(2) end -- head back to say mode
else else
speaktypedesc = 'channelYellow' speaktypedesc = 'channelYellow'
end end
@ -560,11 +398,11 @@ function Console.sendCurrentMessage()
g_game.talkPrivate(speaktype.speakType, name, message) g_game.talkPrivate(speaktype.speakType, name, message)
message = applyMessagePrefixies(player:getName(), player:getLevel(), message) message = applyMessagePrefixies(player:getName(), player:getLevel(), message)
Console.addPrivateText(message, speaktype, name, isPrivateCommand, g_game.getCharacterName()) addPrivateText(message, speaktype, name, isPrivateCommand, g_game.getCharacterName())
end end
end end
function Console.sayModeChange(sayMode) function sayModeChange(sayMode)
local buttom = consolePanel:getChildById('sayModeButton') local buttom = consolePanel:getChildById('sayModeButton')
if sayMode == nil then if sayMode == nil then
sayMode = buttom.sayMode + 1 sayMode = buttom.sayMode + 1
@ -576,11 +414,170 @@ function Console.sayModeChange(sayMode)
buttom.sayMode = sayMode buttom.sayMode = sayMode
end end
function Console.getOwnPrivateTab() function getOwnPrivateTab()
if not ownPrivateName then return end if not ownPrivateName then return end
return Console.getTab(ownPrivateName) return getTab(ownPrivateName)
end end
function Console.ignoreNpcMessages(ignore) function ignoreNpcMessages(ignore)
ignoreNpcMessages = ignore ignoreNpcMessages = ignore
end end
function navigateMessageHistory(step)
local numCommands = #messageHistory
if numCommands > 0 then
currentMessageIndex = math.min(math.max(currentMessageIndex + step, 0), numCommands)
if currentMessageIndex > 0 then
local command = messageHistory[numCommands - currentMessageIndex + 1]
consoleTextEdit:setText(command)
else
consoleTextEdit:clearText()
end
end
end
function applyMessagePrefixies(name, level, message)
if name then
if Options.getOption('showLevelsInConsole') and level > 0 then
message = name .. ' [' .. level .. ']: ' .. message
else
message = name .. ': ' .. message
end
end
return message
end
function onCreatureSpeak(name, level, speaktype, message, channelId, creaturePos)
if ignoreNpcMessages and speaktype == SpeakPrivateNpcToPlayer then return end
local defaultMessage = speaktype < 3 and true or false
speaktype = SpeakTypes[speaktype]
if speaktype.hideInConsole then return end
local composedMessage = applyMessagePrefixies(name, level, message)
if speaktype.private then
addPrivateText(composedMessage, speaktype, name, false, name)
if Options.getOption('showPrivateMessagesOnScreen') then
if(speaktype.speakType ~= SpeakPrivateNpcToPlayer) then
TextMessage.displayPrivate(name .. ':\n' .. message)
end
end
else
local channel = tr('Default')
if not defaultMessage then
channel = channels[channelId]
end
if channel then
addText(composedMessage, speaktype, channel, name)
elseif channelId ~= 0 then
-- server sent a message on a channel that is not open
pwarning('message in channel id ' .. channelId .. ' which is unknown, this is a server bug, relogin if you want to see messages in this channel')
end
end
end
local function onOpenChannel(channelId, channelName)
addChannel(channelName, channelId)
end
local function onOpenPrivateChannel(receiver)
addPrivateChannel(receiver)
end
local function onOpenOwnPrivateChannel(channelId, channelName)
local privateTab = getTab(channelName)
if privateTab == nil then
addChannel(channelName, channelId)
end
ownPrivateName = channelName
end
local function onCloseChannel(channelId)
local channel = channels[channelId]
if channel then
local tab = getTab(channel)
if tab then
consoleTabBar:removeTab(tab)
end
for k, v in pairs(channels) do
if (k == tab.channelId) then channels[k] = nil end
end
end
end
local function doChannelListSubmit()
local channelListPanel = channelsWindow:getChildById('channelList')
local openPrivateChannelWith = channelsWindow:getChildById('openPrivateChannelWith'):getText()
if openPrivateChannelWith ~= '' then
g_game.openPrivateChannel(openPrivateChannelWith)
else
local selectedChannelLabel = channelListPanel:getFocusedChild()
if not selectedChannelLabel then return end
if selectedChannelLabel.channelId == 0xFFFF then
g_game.openOwnChannel()
else
g_game.joinChannel(selectedChannelLabel.channelId)
end
end
channelsWindow:destroy()
end
local function onChannelList(channelList)
if channelsWindow then channelsWindow:destroy() end
channelsWindow = g_ui.displayUI('channelswindow.otui')
local channelListPanel = channelsWindow:getChildById('channelList')
channelsWindow.onEnter = doChannelListSubmit
channelsWindow.onDestroy = function() channelsWindow = nil end
g_keyboard.bindKeyPress('Down', function() channelListPanel:focusNextChild(KeyboardFocusReason) end, channelsWindow)
g_keyboard.bindKeyPress('Up', function() channelListPanel:focusPreviousChild(KeyboardFocusReason) end, channelsWindow)
for k,v in pairs(channelList) do
local channelId = v[1]
local channelName = v[2]
if #channelName > 0 then
local label = g_ui.createWidget('ChannelListLabel', channelListPanel)
label.channelId = channelId
label:setText(channelName)
label:setPhantom(false)
label.onDoubleClick = doChannelListSubmit
end
end
end
local function onGameStart()
-- open last channels
local player = g_game.getLocalPlayer()
if(player) then
local char = player:getName()
local lastChannelsOpen = g_settings.getNode('LastChannelsOpen')
if(not table.empty(lastChannelsOpen) and lastChannelsOpen[char]) then
for channelName, channelId in ipairs(lastChannelsOpen[char]) do
channelId = tonumber(channelId)
if channelId ~= 0 then
if not table.find(channels, channelId) then
g_game.joinChannel(channelId)
end
end
end
end
end
local tab = getTab(tr('Default'))
if tab then
--[[
Known Issue: The server is calling to open channels after
onGameStart is executed causing it to focus the last tab opened.
Fix: Don't save channels to the settings that are opened by the server.
]]
addEvent(function() consoleTabBar:selectTab(tab) end, true)
end
end

@ -3,13 +3,7 @@ Module
description: Manage chat window description: Manage chat window
author: edubart, andrefaramir, baxnie, sn4ake, BeniS author: edubart, andrefaramir, baxnie, sn4ake, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ console.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'console'
Console.init()
@onUnload: |
Console.terminate()

@ -71,7 +71,7 @@ Panel
enabled: false enabled: false
margin-right: 5 margin-right: 5
margin-top: 6 margin-top: 6
@onClick: Console.removeCurrentTab() @onClick: removeCurrentTab()
TabButton TabButton
id: clearChannelButton id: clearChannelButton
@ -118,7 +118,7 @@ Panel
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
margin-left: 6 margin-left: 6
margin-bottom: 6 margin-bottom: 6
@onClick: Console.sayModeChange() @onClick: sayModeChange()
TextEdit TextEdit
id: consoleTextEdit id: consoleTextEdit

@ -1,4 +1,41 @@
Containers = {} function init()
g_ui.importStyle('container.otui')
connect(Container, { onOpen = onContainerOpen,
onClose = onContainerClose,
onAddItem = onContainerAddItem,
onUpdateItem = onContainerUpdateItem,
onRemoveItem = onContainerRemoveItem })
connect(Game, { onGameEnd = clean() })
reloadContainers()
end
function terminate()
disconnect(Container, { onOpen = onContainerOpen,
onClose = onContainerClose,
onAddItem = onContainerAddItem,
onUpdateItem = onContainerUpdateItem,
onRemoveItem = onContainerRemoveItem })
disconnect(Game, { onGameEnd = clean() })
end
function reloadContainers()
clean()
for containerid,container in pairs(g_game.getContainers()) do
onContainerOpen(container)
end
end
function clean()
for containerid,container in pairs(g_game.getContainers()) do
if container.window then
container.window:destroy()
container.window = nil
container.itemsPanel = nil
end
end
end
local function refreshContainerItems(container) local function refreshContainerItems(container)
for slot=0,container:getCapacity()-1 do for slot=0,container:getCapacity()-1 do
@ -14,7 +51,7 @@ local function onContainerOpen(container, previousContainer)
previousContainer.window = nil previousContainer.window = nil
previousContainer.itemsPanel = nil previousContainer.itemsPanel = nil
else else
containerWindow = g_ui.createWidget('ContainerWindow', GameInterface.getRightPanel()) containerWindow = g_ui.createWidget('ContainerWindow', modules.game_interface.getRightPanel())
end end
containerWindow:setId('container' .. container:getId()) containerWindow:setId('container' .. container:getId())
local containerPanel = containerWindow:getChildById('contentsPanel') local containerPanel = containerWindow:getChildById('contentsPanel')
@ -72,43 +109,3 @@ local function onContainerRemoveItem(container, slot, item)
if not container.window then return end if not container.window then return end
refreshContainerItems(container) refreshContainerItems(container)
end end
function Containers.init()
g_ui.importStyle('container.otui')
connect(Container, { onOpen = onContainerOpen,
onClose = onContainerClose,
onAddItem = onContainerAddItem,
onUpdateItem = onContainerUpdateItem,
onRemoveItem = onContainerRemoveItem })
connect(Game, { onGameEnd = Containers.clean() })
Containers.reloadContainers()
end
function Containers.terminate()
disconnect(Container, { onOpen = onContainerOpen,
onClose = onContainerClose,
onAddItem = onContainerAddItem,
onUpdateItem = onContainerUpdateItem,
onRemoveItem = onContainerRemoveItem })
disconnect(Game, { onGameEnd = Containers.clean() })
Containers = nil
end
function Containers.reloadContainers()
Containers.clean()
for containerid,container in pairs(g_game.getContainers()) do
onContainerOpen(container)
end
end
function Containers.clean()
for containerid,container in pairs(g_game.getContainers()) do
if container.window then
container.window:destroy()
container.window = nil
container.itemsPanel = nil
end
end
end

@ -3,13 +3,7 @@ Module
description: Manage containers description: Manage containers
author: edubart, baxnie author: edubart, baxnie
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [containers.lua]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'containers'
Containers.init()
@onUnload: |
Containers.terminate()

@ -1,7 +1,4 @@
HealthInfo = {} Icons = {}
-- constants
local Icons = {}
Icons[1] = { tooltip = tr('You are poisoned'), path = '/game_healthinfo/icons/poisoned.png', id = 'condition_poisoned' } Icons[1] = { tooltip = tr('You are poisoned'), path = '/game_healthinfo/icons/poisoned.png', id = 'condition_poisoned' }
Icons[2] = { tooltip = tr('You are burning'), path = '/game_healthinfo/icons/burning.png', id = 'condition_burning' } Icons[2] = { tooltip = tr('You are burning'), path = '/game_healthinfo/icons/burning.png', id = 'condition_burning' }
Icons[4] = { tooltip = tr('You are electrified'), path = '/game_healthinfo/icons/electrified.png', id = 'condition_electrified' } Icons[4] = { tooltip = tr('You are electrified'), path = '/game_healthinfo/icons/electrified.png', id = 'condition_electrified' }
@ -20,28 +17,26 @@ Icons[16384] = { tooltip = tr('You are within a protection zone'), path = '/game
Icons[32768] = { tooltip = tr('You are bleeding'), path = '/game_healthinfo/icons/bleeding.png', id = 'condition_bleeding' } Icons[32768] = { tooltip = tr('You are bleeding'), path = '/game_healthinfo/icons/bleeding.png', id = 'condition_bleeding' }
Icons[65536] = { tooltip = tr('You are hungry'), path = '/game_healthinfo/icons/hungry.png', id = 'condition_hungry' } Icons[65536] = { tooltip = tr('You are hungry'), path = '/game_healthinfo/icons/hungry.png', id = 'condition_hungry' }
-- private variables healthInfoWindow = nil
local healthInfoWindow healthBar = nil
local healthBar manaBar = nil
local manaBar soulBar = nil
local soulBar healthLabel = nil
local healthLabel manaLabel = nil
local manaLabel soulLabel = nil
local soulLabel capLabel = nil
local capLabel
function init()
-- public functions connect(LocalPlayer, { onHealthChange = onHealthChange,
function HealthInfo.init() onManaChange = onManaChange,
connect(LocalPlayer, { onHealthChange = HealthInfo.onHealthChange, onStatesChange = onStatesChange,
onManaChange = HealthInfo.onManaChange, onSoulChange = onSoulChange,
onStatesChange = HealthInfo.onStatesChange, onFreeCapacityChange = onFreeCapacityChange })
onSoulChange = HealthInfo.onSoulChange,
onFreeCapacityChange = HealthInfo.onFreeCapacityChange }) connect(g_game, { onGameEnd = offline })
connect(g_game, { onGameEnd = HealthInfo.offline }) healthInfoWindow = g_ui.loadUI('healthinfo.otui', modules.game_interface.getRightPanel())
healthInfoButton = TopMenu.addRightGameToggleButton('healthInfoButton', tr('Health Information'), 'healthinfo.png', toggle)
healthInfoWindow = g_ui.loadUI('healthinfo.otui', GameInterface.getRightPanel())
healthInfoButton = TopMenu.addRightGameToggleButton('healthInfoButton', tr('Health Information'), 'healthinfo.png', HealthInfo.toggle)
healthInfoWindow:disableResize() healthInfoWindow:disableResize()
healthInfoButton:setOn(true) healthInfoButton:setOn(true)
healthBar = healthInfoWindow:recursiveGetChildById('healthBar') healthBar = healthInfoWindow:recursiveGetChildById('healthBar')
@ -54,22 +49,22 @@ function HealthInfo.init()
if g_game.isOnline() then if g_game.isOnline() then
local localPlayer = g_game.getLocalPlayer() local localPlayer = g_game.getLocalPlayer()
HealthInfo.onHealthChange(localPlayer, localPlayer:getHealth(), localPlayer:getMaxHealth()) onHealthChange(localPlayer, localPlayer:getHealth(), localPlayer:getMaxHealth())
HealthInfo.onManaChange(localPlayer, localPlayer:getMana(), localPlayer:getMaxMana()) onManaChange(localPlayer, localPlayer:getMana(), localPlayer:getMaxMana())
HealthInfo.onStatesChange(localPlayer, localPlayer:getStates(), 0) onStatesChange(localPlayer, localPlayer:getStates(), 0)
HealthInfo.onSoulChange(localPlayer, localPlayer:getSoul()) onSoulChange(localPlayer, localPlayer:getSoul())
HealthInfo.onFreeCapacityChange(localPlayer, localPlayer:getFreeCapacity()) onFreeCapacityChange(localPlayer, localPlayer:getFreeCapacity())
end end
end end
function HealthInfo.terminate() function terminate()
disconnect(LocalPlayer, { onHealthChange = HealthInfo.onHealthChange, disconnect(LocalPlayer, { onHealthChange = onHealthChange,
onManaChange = HealthInfo.onManaChange, onManaChange = onManaChange,
onStatesChange = HealthInfo.onStatesChange, onStatesChange = onStatesChange,
onSoulChange = HealthInfo.onSoulChange, onSoulChange = onSoulChange,
onFreeCapacityChange = HealthInfo.onFreeCapacityChange }) onFreeCapacityChange = onFreeCapacityChange })
disconnect(g_game, { onGameEnd = HealthInfo.offline }) disconnect(g_game, { onGameEnd = offline })
healthInfoWindow:destroy() healthInfoWindow:destroy()
healthInfoButton:destroy() healthInfoButton:destroy()
@ -88,7 +83,7 @@ function HealthInfo.terminate()
HealthInfo = nil HealthInfo = nil
end end
function HealthInfo.toggle() function toggle()
if healthInfoButton:isOn() then if healthInfoButton:isOn() then
healthInfoWindow:close() healthInfoWindow:close()
healthInfoButton:setOn(false) healthInfoButton:setOn(false)
@ -98,21 +93,21 @@ function HealthInfo.toggle()
end end
end end
function HealthInfo.onMiniWindowClose() function onMiniWindowClose()
healthInfoButton:setOn(false) healthInfoButton:setOn(false)
end end
function HealthInfo.offline() function offline()
healthInfoWindow:recursiveGetChildById('conditionPanel'):destroyChildren() healthInfoWindow:recursiveGetChildById('conditionPanel'):destroyChildren()
end end
-- hooked events -- hooked events
function HealthInfo.onHealthChange(localPlayer, health, maxHealth) function onHealthChange(localPlayer, health, maxHealth)
healthLabel:setText(health .. ' / ' .. maxHealth) healthLabel:setText(health .. ' / ' .. maxHealth)
healthBar:setPercent(health / maxHealth * 100) healthBar:setPercent(health / maxHealth * 100)
end end
function HealthInfo.onManaChange(localPlayer, mana, maxMana) function onManaChange(localPlayer, mana, maxMana)
manaLabel:setText(mana .. ' / ' .. maxMana) manaLabel:setText(mana .. ' / ' .. maxMana)
local percent local percent
@ -124,16 +119,16 @@ function HealthInfo.onManaChange(localPlayer, mana, maxMana)
manaBar:setPercent(percent) manaBar:setPercent(percent)
end end
function HealthInfo.onSoulChange(localPlayer, soul) function onSoulChange(localPlayer, soul)
soulLabel:setText(tr('Soul') .. ': ' .. soul) soulLabel:setText(tr('Soul') .. ': ' .. soul)
end end
function HealthInfo.onFreeCapacityChange(player, freeCapacity) function onFreeCapacityChange(player, freeCapacity)
capLabel:setText(tr('Cap') .. ': ' .. freeCapacity) capLabel:setText(tr('Cap') .. ': ' .. freeCapacity)
end end
function HealthInfo.onStatesChange(localPlayer, now, old) function onStatesChange(localPlayer, now, old)
if now == old then return end if now == old then return end
local bitsChanged = bit32.bxor(now, old) local bitsChanged = bit32.bxor(now, old)
@ -142,12 +137,12 @@ function HealthInfo.onStatesChange(localPlayer, now, old)
if pow > bitsChanged then break end if pow > bitsChanged then break end
local bitChanged = bit32.band(bitsChanged, pow) local bitChanged = bit32.band(bitsChanged, pow)
if bitChanged ~= 0 then if bitChanged ~= 0 then
HealthInfo.toggleIcon(bitChanged) toggleIcon(bitChanged)
end end
end end
end end
function HealthInfo.toggleIcon(bitChanged) function toggleIcon(bitChanged)
local content = healthInfoWindow:recursiveGetChildById('conditionPanel') local content = healthInfoWindow:recursiveGetChildById('conditionPanel')
local icon = content:getChildById(Icons[bitChanged].id) local icon = content:getChildById(Icons[bitChanged].id)

@ -3,13 +3,7 @@ Module
description: Displays health, mana points, soul points, and conditions description: Displays health, mana points, soul points, and conditions
author: edubart, BeniS author: edubart, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ healthinfo.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'healthinfo'
HealthInfo.init()
@onUnload: |
HealthInfo.terminate()

@ -65,7 +65,7 @@ MiniWindow
id: healthInfoWindow id: healthInfoWindow
!text: tr('Health Info') !text: tr('Health Info')
height: 102 height: 102
@onClose: HealthInfo.onMiniWindowClose() @onClose: onMiniWindowClose()
&save: true &save: true
MiniWindowContents MiniWindowContents

@ -1,29 +1,8 @@
HotkeysManager = {}
local hotkeysManagerLoaded = false
local hotkeysWindow
local hotkeysButton
local currentHotkeysList
local hotkeyLabelSelectedOnList
local currentItemPreview
local itemWidget
local addHotkey
local removeHotkey
local hotkeyText
local hotKeyTextLabel
local sendAutomatically
local selectObjectButton
local clearObjectButton
local useOnSelf
local useOnTarget
local useWith
local hotkeyList = {}
HOTKEY_MANAGER_USEONSELF = 1 HOTKEY_MANAGER_USEONSELF = 1
HOTKEY_MANAGER_USEONTARGET = 2 HOTKEY_MANAGER_USEONTARGET = 2
HOTKEY_MANAGER_USEWITH = 3 HOTKEY_MANAGER_USEWITH = 3
local hotkeyColors = { HotkeyColors = {
text = '#888888', text = '#888888',
textAutoSend = '#FFFFFF', textAutoSend = '#FFFFFF',
itemUse = '#8888FF', itemUse = '#8888FF',
@ -32,14 +11,33 @@ local hotkeyColors = {
itemUseWith = '#CC0000', itemUseWith = '#CC0000',
} }
hotkeysManagerLoaded = false
hotkeysWindow = nil
hotkeysButton = nil
currentHotkeysList = nil
hotkeyLabelSelectedOnList = nil
currentItemPreview = nil
itemWidget = nil
addHotkey = nil
removeHotkey = nil
hotkeyText = nil
hotKeyTextLabel = nil
sendAutomatically = nil
selectObjectButton = nil
clearObjectButton = nil
useOnSelf = nil
useOnTarget = nil
useWith = nil
hotkeyList = {}
-- public functions -- public functions
function HotkeysManager.init() function init()
hotkeysWindow = g_ui.displayUI('hotkeys_manager.otui') hotkeysWindow = g_ui.displayUI('hotkeys_manager.otui')
local hotkeyListPanel = hotkeysWindow:getChildById('currentHotkeys') local hotkeyListPanel = hotkeysWindow:getChildById('currentHotkeys')
hotkeysWindow:setVisible(false) hotkeysWindow:setVisible(false)
hotkeysButton = TopMenu.addLeftGameButton('hotkeysButton', tr('Hotkeys') .. ' (Ctrl+K)', '/game_hotkeys/icon.png', HotkeysManager.toggle) hotkeysButton = TopMenu.addLeftGameButton('hotkeysButton', tr('Hotkeys') .. ' (Ctrl+K)', '/game_hotkeys/icon.png', toggle)
g_keyboard.bindKeyDown('Ctrl+K', HotkeysManager.toggle) g_keyboard.bindKeyDown('Ctrl+K', toggle)
g_keyboard.bindKeyPress('Down', function() hotkeyListPanel:focusNextChild(KeyboardFocusReason) end, hotkeysWindow) g_keyboard.bindKeyPress('Down', function() hotkeyListPanel:focusNextChild(KeyboardFocusReason) end, hotkeysWindow)
g_keyboard.bindKeyPress('Up', function() hotkeyListPanel:focusPreviousChild(KeyboardFocusReason) end, hotkeysWindow) g_keyboard.bindKeyPress('Up', function() hotkeyListPanel:focusPreviousChild(KeyboardFocusReason) end, hotkeysWindow)
@ -61,21 +59,39 @@ function HotkeysManager.init()
itemWidget:setVisible(false) itemWidget:setVisible(false)
itemWidget:setFocusable(false) itemWidget:setFocusable(false)
connect(g_game, { onGameEnd = HotkeysManager.hide }) connect(g_game, { onGameEnd = hide })
connect(currentHotkeysList, { onChildFocusChange = function (self, focusedChild) HotkeysManager.checkSelectedHotkey(focusedChild) end } ) connect(currentHotkeysList, { onChildFocusChange = function (self, focusedChild) checkSelectedHotkey(focusedChild) end } )
hotkeysManagerLoaded = true hotkeysManagerLoaded = true
HotkeysManager.load() load()
end
function terminate()
hotkeysManagerLoaded = false
disconnect(g_game, { onGameEnd = hide })
g_keyboard.unbindKeyDown('Ctrl+K')
save()
for keyCombo,v in pairs(hotkeyList) do
g_keyboard.unbindKeyPress(keyCombo)
end
hotkeyList = {}
itemWidget:destroy()
hotkeysWindow:destroy()
hotkeysButton:destroy()
end end
function HotkeysManager.load() function load()
local hotkeySettings = g_settings.getNode('HotkeysManager') local hotkeySettings = g_settings.getNode('HotkeysManager')
local hasCombos = false local hasCombos = false
if hotkeySettings ~= nil then if hotkeySettings ~= nil then
for i, v in pairs(hotkeySettings) do for i, v in pairs(hotkeySettings) do
HotkeysManager.addKeyCombo(nil, v.keyCombo, v) addKeyCombo(nil, v.keyCombo, v)
hasCombos = true hasCombos = true
end end
end end
@ -83,12 +99,12 @@ function HotkeysManager.load()
-- add default F keys combos -- add default F keys combos
if not hasCombos then if not hasCombos then
for i=1,12 do for i=1,12 do
HotkeysManager.addKeyCombo(nil, 'F' .. i) addKeyCombo(nil, 'F' .. i)
end end
end end
end end
function HotkeysManager.save() function save()
local hotkeySettings = {} local hotkeySettings = {}
for i=1, currentHotkeysList:getChildCount() do for i=1, currentHotkeysList:getChildCount() do
local child = currentHotkeysList:getChildByIndex(i) local child = currentHotkeysList:getChildByIndex(i)
@ -102,49 +118,15 @@ function HotkeysManager.save()
g_settings.setNode('HotkeysManager', hotkeySettings) g_settings.setNode('HotkeysManager', hotkeySettings)
end end
function HotkeysManager.terminate() function toggle()
hotkeysManagerLoaded = false
disconnect(g_game, { onGameEnd = HotkeysManager.hide })
g_keyboard.unbindKeyDown('Ctrl+K')
HotkeysManager.save()
currentHotkeysList = nil
hotkeyLabelSelectedOnList = nil
currentItemPreview = nil
hotkeyList = {}
addHotkey = nil
removeHotkey = nil
hotkeyText = nil
hotKeyTextLabel = nil
sendAutomatically = nil
selectObjectButton = nil
clearObjectButton = nil
useOnSelf = nil
useOnTarget = nil
useWith = nil
itemWidget:destroy()
itemWidget = nil
hotkeysWindow:destroy()
hotkeysWindow = nil
hotkeysButton:destroy()
hotkeysButton = nil
HotkeysManager = nil
end
function HotkeysManager.toggle()
if hotkeysWindow:isVisible() then if hotkeysWindow:isVisible() then
HotkeysManager.hide() hide()
else else
HotkeysManager.show() show()
end end
end end
function HotkeysManager.show() function show()
if g_game.isOnline() then if g_game.isOnline() then
hotkeysWindow:grabKeyboard() hotkeysWindow:grabKeyboard()
hotkeysWindow:show() hotkeysWindow:show()
@ -152,16 +134,16 @@ function HotkeysManager.show()
end end
end end
function HotkeysManager.hide() function hide()
hotkeysWindow:ungrabKeyboard() hotkeysWindow:ungrabKeyboard()
hotkeysWindow:hide() hotkeysWindow:hide()
end end
-- private functions -- private functions
function HotkeysManager.onChooseItemMouseRelease(self, mousePosition, mouseButton) function onChooseItemMouseRelease(self, mousePosition, mouseButton)
local item = nil local item = nil
if mouseButton == MouseLeftButton then if mouseButton == MouseLeftButton then
local clickedWidget = GameInterface.getRootPanel():recursiveGetChildByPos(mousePosition, false) local clickedWidget = modules.game_interface.getRootPanel():recursiveGetChildByPos(mousePosition, false)
if clickedWidget then if clickedWidget then
if clickedWidget:getClassName() == 'UIMap' then if clickedWidget:getClassName() == 'UIMap' then
local tile = clickedWidget:getTile(mousePosition) local tile = clickedWidget:getTile(mousePosition)
@ -180,8 +162,8 @@ function HotkeysManager.onChooseItemMouseRelease(self, mousePosition, mouseButto
if item then if item then
currentItemPreview:setItemId(item:getId()) currentItemPreview:setItemId(item:getId())
hotkeyLabelSelectedOnList.itemId = item:getId() hotkeyLabelSelectedOnList.itemId = item:getId()
HotkeysManager.changeUseType(HOTKEY_MANAGER_USEONSELF) changeUseType(HOTKEY_MANAGER_USEONSELF)
HotkeysManager.checkSelectedHotkey(hotkeyLabelSelectedOnList) checkSelectedHotkey(hotkeyLabelSelectedOnList)
HotkeysManager:show() HotkeysManager:show()
end end
@ -190,12 +172,12 @@ function HotkeysManager.onChooseItemMouseRelease(self, mousePosition, mouseButto
self:destroy() self:destroy()
end end
function HotkeysManager.startChooseItem() function startChooseItem()
local mouseGrabberWidget = g_ui.createWidget('UIWidget') local mouseGrabberWidget = g_ui.createWidget('UIWidget')
mouseGrabberWidget:setVisible(false) mouseGrabberWidget:setVisible(false)
mouseGrabberWidget:setFocusable(false) mouseGrabberWidget:setFocusable(false)
connect(mouseGrabberWidget, { onMouseRelease = HotkeysManager.onChooseItemMouseRelease }) connect(mouseGrabberWidget, { onMouseRelease = onChooseItemMouseRelease })
mouseGrabberWidget:grabMouse() mouseGrabberWidget:grabMouse()
g_mouse.setTargetCursor() g_mouse.setTargetCursor()
@ -203,17 +185,17 @@ function HotkeysManager.startChooseItem()
HotkeysManager:hide() HotkeysManager:hide()
end end
function HotkeysManager.clearObject() function clearObject()
hotkeyLabelSelectedOnList.itemId = nil hotkeyLabelSelectedOnList.itemId = nil
currentItemPreview:clearItem() currentItemPreview:clearItem()
HotkeysManager.changeUseType(HOTKEY_MANAGER_USEONSELF) changeUseType(HOTKEY_MANAGER_USEONSELF)
HotkeysManager.sendAutomatically(false) setSendAutomatically(false)
hotkeyLabelSelectedOnList:setText(hotkeyLabelSelectedOnList.keyCombo .. ': ') hotkeyLabelSelectedOnList:setText(hotkeyLabelSelectedOnList.keyCombo .. ': ')
HotkeysManager.checkSelectedHotkey(hotkeyLabelSelectedOnList) checkSelectedHotkey(hotkeyLabelSelectedOnList)
end end
function HotkeysManager.addHotkey() function addHotkey()
local widget local widget
messageBox = g_ui.createWidget('MainWindow', rootWidget) messageBox = g_ui.createWidget('MainWindow', rootWidget)
@ -260,26 +242,26 @@ function HotkeysManager.addHotkey()
widget:setMarginRight(10) widget:setMarginRight(10)
widget.onClick = function (self) widget.onClick = function (self)
messageBox = nil messageBox = nil
HotkeysManager.addKeyCombo(self:getParent(), self:getParent():getChildById('comboPreview').keyCombo) addKeyCombo(self:getParent(), self:getParent():getChildById('comboPreview').keyCombo)
end end
connect(messageBox, { onKeyDown = HotkeysManager.hotkeyCapture }, true) connect(messageBox, { onKeyDown = hotkeyCapture }, true)
end end
function HotkeysManager.addKeyCombo(messageBox, keyCombo, keySettings) function addKeyCombo(messageBox, keyCombo, keySettings)
local label = nil local label = nil
if currentHotkeysList:getChildById(keyCombo) == nil then if currentHotkeysList:getChildById(keyCombo) == nil then
local label = g_ui.createWidget('HotkeyListLabel', currentHotkeysList) local label = g_ui.createWidget('HotkeyListLabel', currentHotkeysList)
label:setId(keyCombo) label:setId(keyCombo)
label:setColor(hotkeyColors.text) label:setColor(HotkeyColors.text)
label:setText(keyCombo..': ') label:setText(keyCombo..': ')
if keySettings then if keySettings then
hotkeyLabelSelectedOnList = label hotkeyLabelSelectedOnList = label
label.keyCombo = keyCombo label.keyCombo = keyCombo
HotkeysManager.sendAutomatically(keySettings.autoSend) setSendAutomatically(keySettings.autoSend)
label.itemId = keySettings.itemId label.itemId = keySettings.itemId
currentItemPreview:setItemId(keySettings.itemId) currentItemPreview:setItemId(keySettings.itemId)
HotkeysManager.changeUseType(tonumber(keySettings.useType)) changeUseType(tonumber(keySettings.useType))
label.value = keySettings.value label.value = keySettings.value
else else
label.keyCombo = keyCombo label.keyCombo = keyCombo
@ -289,10 +271,10 @@ function HotkeysManager.addKeyCombo(messageBox, keyCombo, keySettings)
label.value = '' label.value = ''
end end
HotkeysManager.checkSelectedHotkey(label) checkSelectedHotkey(label)
hotkeyList[keyCombo] = label hotkeyList[keyCombo] = label
g_keyboard.bindKeyPress(keyCombo, function () HotkeysManager.call(keyCombo) end, nil, 350) g_keyboard.bindKeyPress(keyCombo, function () call(keyCombo) end, nil, 350)
end end
if messageBox then if messageBox then
@ -301,14 +283,14 @@ function HotkeysManager.addKeyCombo(messageBox, keyCombo, keySettings)
end end
end end
function HotkeysManager.call(keyCombo) function call(keyCombo)
if g_game.isOnline() then if g_game.isOnline() then
local hotKey = hotkeyList[keyCombo] local hotKey = hotkeyList[keyCombo]
if hotKey ~= nil and hotKey.itemId == nil and hotKey.value ~= '' then if hotKey ~= nil and hotKey.itemId == nil and hotKey.value ~= '' then
if hotKey.autoSend then if hotKey.autoSend then
g_game.talk(hotKey.value) g_game.talk(hotKey.value)
else else
Console.setTextEditText(hotKey.value) modules.game_console.setTextEditText(hotKey.value)
end end
elseif hotKey.itemId ~= nil then elseif hotKey.itemId ~= nil then
if hotKey.useType == HOTKEY_MANAGER_USEONSELF then if hotKey.useType == HOTKEY_MANAGER_USEONSELF then
@ -320,13 +302,13 @@ function HotkeysManager.call(keyCombo)
end end
elseif hotKey.useType == HOTKEY_MANAGER_USEWITH then elseif hotKey.useType == HOTKEY_MANAGER_USEWITH then
itemWidget:setItemId(hotKey.itemId) itemWidget:setItemId(hotKey.itemId)
GameInterface.startUseWith(itemWidget:getItem()) modules.game_interface.startUseWith(itemWidget:getItem())
end end
end end
end end
end end
function HotkeysManager.checkSelectedHotkey(focused) function checkSelectedHotkey(focused)
if not focused then return end if not focused then return end
if hotkeysManagerLoaded then if hotkeysManagerLoaded then
hotkeyLabelSelectedOnList = focused hotkeyLabelSelectedOnList = focused
@ -362,7 +344,7 @@ function HotkeysManager.checkSelectedHotkey(focused)
currentItemPreview:setItemId(hotkeyLabelSelectedOnList.itemId) currentItemPreview:setItemId(hotkeyLabelSelectedOnList.itemId)
end end
HotkeysManager.changeUseType(hotkeyLabelSelectedOnList.useType) changeUseType(hotkeyLabelSelectedOnList.useType)
else else
hotkeyText:clearText() hotkeyText:clearText()
removeHotkey:disable() removeHotkey:disable()
@ -383,7 +365,7 @@ function HotkeysManager.checkSelectedHotkey(focused)
end end
end end
function HotkeysManager.changeUseType(useType, checked) function changeUseType(useType, checked)
if checked == nil or checked then if checked == nil or checked then
hotkeyLabelSelectedOnList.useType = useType hotkeyLabelSelectedOnList.useType = useType
if hotkeyLabelSelectedOnList.itemId ~= nil and currentItemPreview:getItem():isMultiUse() then if hotkeyLabelSelectedOnList.itemId ~= nil and currentItemPreview:getItem():isMultiUse() then
@ -393,19 +375,19 @@ function HotkeysManager.changeUseType(useType, checked)
if useType == HOTKEY_MANAGER_USEONSELF then if useType == HOTKEY_MANAGER_USEONSELF then
hotkeyLabelSelectedOnList:setText(tr('%s: (use object on yourself)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setText(tr('%s: (use object on yourself)', hotkeyLabelSelectedOnList.keyCombo))
hotkeyLabelSelectedOnList:setColor(hotkeyColors.itemUseSelf) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUseSelf)
useOnSelf:setChecked(true) useOnSelf:setChecked(true)
useOnTarget:setChecked(false) useOnTarget:setChecked(false)
useWith:setChecked(false) useWith:setChecked(false)
elseif useType == HOTKEY_MANAGER_USEONTARGET then elseif useType == HOTKEY_MANAGER_USEONTARGET then
hotkeyLabelSelectedOnList:setText(tr('%s: (use object on target)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setText(tr('%s: (use object on target)', hotkeyLabelSelectedOnList.keyCombo))
hotkeyLabelSelectedOnList:setColor(hotkeyColors.itemUseTarget) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUseTarget)
useOnSelf:setChecked(false) useOnSelf:setChecked(false)
useOnTarget:setChecked(true) useOnTarget:setChecked(true)
useWith:setChecked(false) useWith:setChecked(false)
elseif useType == HOTKEY_MANAGER_USEWITH then elseif useType == HOTKEY_MANAGER_USEWITH then
hotkeyLabelSelectedOnList:setText(tr('%s: (use object with crosshair)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setText(tr('%s: (use object with crosshair)', hotkeyLabelSelectedOnList.keyCombo))
hotkeyLabelSelectedOnList:setColor(hotkeyColors.itemUseWith) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUseWith)
useOnSelf:setChecked(false) useOnSelf:setChecked(false)
useOnTarget:setChecked(false) useOnTarget:setChecked(false)
@ -417,7 +399,7 @@ function HotkeysManager.changeUseType(useType, checked)
useWith:disable() useWith:disable()
hotkeyLabelSelectedOnList:setText(tr('%s: (use object)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setText(tr('%s: (use object)', hotkeyLabelSelectedOnList.keyCombo))
hotkeyLabelSelectedOnList:setColor(hotkeyColors.itemUse) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUse)
useOnSelf:setChecked(false) useOnSelf:setChecked(false)
useOnTarget:setChecked(false) useOnTarget:setChecked(false)
@ -434,7 +416,7 @@ function HotkeysManager.changeUseType(useType, checked)
end end
end end
function HotkeysManager.removeHotkey() function removeHotkey()
if hotkeyLabelSelectedOnList ~= nil then if hotkeyLabelSelectedOnList ~= nil then
hotkeyList[hotkeyLabelSelectedOnList.keyCombo] = nil hotkeyList[hotkeyLabelSelectedOnList.keyCombo] = nil
g_keyboard.unbindKeyPress(hotkeyLabelSelectedOnList.keyCombo) g_keyboard.unbindKeyPress(hotkeyLabelSelectedOnList.keyCombo)
@ -442,7 +424,7 @@ function HotkeysManager.removeHotkey()
end end
end end
function HotkeysManager.onHotkeyTextChange(id, value) function onHotkeyTextChange(id, value)
if hotkeyLabelSelectedOnList ~= nil and hotkeyLabelSelectedOnList.keyCombo ~= nil then if hotkeyLabelSelectedOnList ~= nil and hotkeyLabelSelectedOnList.keyCombo ~= nil then
hotkeyLabelSelectedOnList:setText(hotkeyLabelSelectedOnList.keyCombo .. ': ' .. value) hotkeyLabelSelectedOnList:setText(hotkeyLabelSelectedOnList.keyCombo .. ': ' .. value)
hotkeyLabelSelectedOnList.value = value hotkeyLabelSelectedOnList.value = value
@ -456,16 +438,16 @@ function HotkeysManager.onHotkeyTextChange(id, value)
end end
end end
function HotkeysManager.sendAutomatically(value) function setSendAutomatically(value)
hotkeyLabelSelectedOnList.autoSend = value hotkeyLabelSelectedOnList.autoSend = value
if value then if value then
hotkeyLabelSelectedOnList:setColor(hotkeyColors.autoSend) hotkeyLabelSelectedOnList:setColor(HotkeyColors.autoSend)
else else
hotkeyLabelSelectedOnList:setColor(hotkeyColors.text) hotkeyLabelSelectedOnList:setColor(HotkeyColors.text)
end end
end end
function HotkeysManager.hotkeyCapture(widget, keyCode, keyboardModifiers) function hotkeyCapture(widget, keyCode, keyboardModifiers)
local keyCombo = determineKeyComboDesc(keyCode, keyboardModifiers) local keyCombo = determineKeyComboDesc(keyCode, keyboardModifiers)
local comboPreview = rootWidget:getChildById('assignWindow'):getChildById('comboPreview') local comboPreview = rootWidget:getChildById('assignWindow'):getChildById('comboPreview')
comboPreview:setText(tr('Current hotkey to add: %s', keyCombo)) comboPreview:setText(tr('Current hotkey to add: %s', keyCombo))

@ -3,13 +3,7 @@ Module
description: Manage client hotkeys description: Manage client hotkeys
author: andrefaramir, BeniS author: andrefaramir, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ hotkeys_manager.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'hotkeys_manager'
HotkeysManager.init()
@onUnload: |
HotkeysManager.terminate()

@ -13,8 +13,8 @@ MainWindow
!text: tr('Hotkeys') !text: tr('Hotkeys')
size: 340 460 size: 340 460
@onEnter: HotkeysManager.hide() @onEnter: hide()
@onEscape: HotkeysManager.hide() @onEscape: hide()
Label Label
id: currentHotkeysLabel id: currentHotkeysLabel
@ -33,7 +33,7 @@ MainWindow
TextList TextList
id: currentHotkeys id: currentHotkeys
vertical-scrollbar: currentHotkeysScrollBar vertical-scrollbar: currentHotkeysScrollBar
anchors.left: parent.left anchors.left: parent.left
anchors.right: prev.left anchors.right: prev.left
anchors.top: prev.top anchors.top: prev.top
@ -56,7 +56,7 @@ MainWindow
anchors.left: parent.left anchors.left: parent.left
anchors.top: prev.bottom anchors.top: prev.bottom
margin-top: 2 margin-top: 2
@onClick: HotkeysManager.addHotkey() @onClick: addHotkey()
Button Button
id: removeHotkey id: removeHotkey
@ -66,7 +66,7 @@ MainWindow
anchors.left: prev.right anchors.left: prev.right
anchors.top: prev.top anchors.top: prev.top
margin-left: 10 margin-left: 10
@onClick: HotkeysManager.removeHotkey() @onClick: removeHotkey()
Label Label
id: hotKeyTextLabel id: hotKeyTextLabel
@ -84,7 +84,7 @@ MainWindow
anchors.right: parent.right anchors.right: parent.right
anchors.top: prev.bottom anchors.top: prev.bottom
margin-bottom: 2 margin-bottom: 2
@onTextChange: HotkeysManager.onHotkeyTextChange(self:getId(), self:getText()) @onTextChange: onHotkeyTextChange(self:getId(), self:getText())
CheckBox CheckBox
id: sendAutomatically id: sendAutomatically
@ -94,7 +94,7 @@ MainWindow
anchors.top: prev.bottom anchors.top: prev.bottom
enabled:false enabled:false
margin-top: 10 margin-top: 10
@onCheckChange: HotkeysManager.sendAutomatically(self:isChecked()) @onCheckChange: setSendAutomatically(self:isChecked())
Item Item
id: itemPreview id: itemPreview
@ -111,7 +111,7 @@ MainWindow
anchors.left: prev.right anchors.left: prev.right
anchors.top: prev.top anchors.top: prev.top
margin-left: 10 margin-left: 10
@onClick: HotkeysManager.startChooseItem() @onClick: startChooseItem()
Button Button
id: clearObjectButton id: clearObjectButton
@ -122,7 +122,7 @@ MainWindow
anchors.right: prev.right anchors.right: prev.right
anchors.top: prev.bottom anchors.top: prev.bottom
margin-top: 2 margin-top: 2
@onClick: HotkeysManager.clearObject() @onClick: clearObject()
ButtonBox ButtonBox
id: useOnSelf id: useOnSelf
@ -134,7 +134,7 @@ MainWindow
anchors.top: selectObjectButton.top anchors.top: selectObjectButton.top
checked: false checked: false
margin-left: 10 margin-left: 10
@onCheckChange: HotkeysManager.changeUseType(HOTKEY_MANAGER_USEONSELF, self:isChecked()) @onCheckChange: changeUseType(HOTKEY_MANAGER_USEONSELF, self:isChecked())
ButtonBox ButtonBox
id: useOnTarget id: useOnTarget
@ -146,7 +146,7 @@ MainWindow
anchors.top: prev.bottom anchors.top: prev.bottom
checked: false checked: false
margin-top: 2 margin-top: 2
@onCheckChange: HotkeysManager.changeUseType(HOTKEY_MANAGER_USEONTARGET, self:isChecked()) @onCheckChange: changeUseType(HOTKEY_MANAGER_USEONTARGET, self:isChecked())
ButtonBox ButtonBox
id: useWith id: useWith
@ -158,11 +158,11 @@ MainWindow
anchors.top: prev.bottom anchors.top: prev.bottom
checked: false checked: false
margin-top: 2 margin-top: 2
@onCheckChange: HotkeysManager.changeUseType(HOTKEY_MANAGER_USEWITH, self:isChecked()) @onCheckChange: changeUseType(HOTKEY_MANAGER_USEWITH, self:isChecked())
Button Button
!text: tr('Close') !text: tr('Close')
width: 64 width: 64
anchors.right: parent.right anchors.right: parent.right
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
@onClick: HotkeysManager.hide() @onClick: hide()

@ -1,41 +1,30 @@
GameInterface = {} WALK_AUTO_REPEAT_DELAY = 90
local WALK_AUTO_REPEAT_DELAY = 90 gameRootPanel = nil
local gameRootPanel gameMapPanel = nil
local gameMapPanel gameRightPanel = nil
local gameRightPanel gameLeftPanel = nil
local gameLeftPanel gameBottomPanel = nil
local gameBottomPanel logoutButton = nil
local logoutButton mouseGrabberWidget = nil
local mouseGrabberWidget countWindow = nil
logoutWindow = nil
local countWindow exitWindow = nil
local logoutWindow
local exitWindow function init()
local function onLeftPanelVisibilityChange(leftPanel, visible)
if not visible then
local children = leftPanel:getChildren()
for i=1,#children do
children[i]:setParent(gameRightPanel)
end
end
end
function GameInterface.init()
g_ui.importStyle('styles/countwindow.otui') g_ui.importStyle('styles/countwindow.otui')
g_ui.importStyle('styles/logoutwindow.otui') g_ui.importStyle('styles/logoutwindow.otui')
g_ui.importStyle('styles/exitwindow.otui') g_ui.importStyle('styles/exitwindow.otui')
connect(g_game, { onGameStart = GameInterface.show, connect(g_game, { onGameStart = show,
onGameEnd = GameInterface.hide }, true) onGameEnd = hide }, true)
gameRootPanel = g_ui.displayUI('gameinterface.otui') gameRootPanel = g_ui.displayUI('gameinterface.otui')
gameRootPanel:hide() gameRootPanel:hide()
gameRootPanel:lower() gameRootPanel:lower()
mouseGrabberWidget = gameRootPanel:getChildById('mouseGrabber') mouseGrabberWidget = gameRootPanel:getChildById('mouseGrabber')
mouseGrabberWidget.onMouseRelease = GameInterface.onMouseGrabberRelease mouseGrabberWidget.onMouseRelease = onMouseGrabberRelease
gameMapPanel = gameRootPanel:getChildById('gameMapPanel') gameMapPanel = gameRootPanel:getChildById('gameMapPanel')
gameRightPanel = gameRootPanel:getChildById('gameRightPanel') gameRightPanel = gameRootPanel:getChildById('gameRightPanel')
@ -43,7 +32,7 @@ function GameInterface.init()
gameBottomPanel = gameRootPanel:getChildById('gameBottomPanel') gameBottomPanel = gameRootPanel:getChildById('gameBottomPanel')
connect(gameLeftPanel, { onVisibilityChange = onLeftPanelVisibilityChange }) connect(gameLeftPanel, { onVisibilityChange = onLeftPanelVisibilityChange })
logoutButton = TopMenu.addRightButton('logoutButton', 'Logout', '/images/logout.png', GameInterface.tryLogout) logoutButton = TopMenu.addRightButton('logoutButton', 'Logout', '/images/logout.png', tryLogout)
logoutButton:hide() logoutButton:hide()
g_keyboard.bindKeyPress('Up', function() g_game.walk(North) end, gameRootPanel, WALK_AUTO_REPEAT_DELAY) g_keyboard.bindKeyPress('Up', function() g_game.walk(North) end, gameRootPanel, WALK_AUTO_REPEAT_DELAY)
@ -69,9 +58,9 @@ function GameInterface.init()
g_keyboard.bindKeyPress('Escape', function() g_game.cancelAttackAndFollow() end, gameRootPanel, WALK_AUTO_REPEAT_DELAY) g_keyboard.bindKeyPress('Escape', function() g_game.cancelAttackAndFollow() end, gameRootPanel, WALK_AUTO_REPEAT_DELAY)
g_keyboard.bindKeyPress('Ctrl+=', function() gameMapPanel:zoomIn() end, gameRootPanel, 250) g_keyboard.bindKeyPress('Ctrl+=', function() gameMapPanel:zoomIn() end, gameRootPanel, 250)
g_keyboard.bindKeyPress('Ctrl+-', function() gameMapPanel:zoomOut() end, gameRootPanel, 250) g_keyboard.bindKeyPress('Ctrl+-', function() gameMapPanel:zoomOut() end, gameRootPanel, 250)
g_keyboard.bindKeyDown('Ctrl+Q', GameInterface.logout, gameRootPanel) g_keyboard.bindKeyDown('Ctrl+Q', logout, gameRootPanel)
g_keyboard.bindKeyDown('Ctrl+L', GameInterface.logout, gameRootPanel) g_keyboard.bindKeyDown('Ctrl+L', logout, gameRootPanel)
g_keyboard.bindKeyDown('Ctrl+W', function() g_map.cleanTexts() TextMessage.clearMessages() end, gameRootPanel) g_keyboard.bindKeyDown('Ctrl+W', function() g_map.cleanTexts() modules.game_textmessage.clearMessages() end, gameRootPanel)
g_keyboard.bindKeyDown('Ctrl+.', function() g_keyboard.bindKeyDown('Ctrl+.', function()
if gameMapPanel:isKeepAspectRatioEnabled() then if gameMapPanel:isKeepAspectRatioEnabled() then
@ -80,35 +69,24 @@ function GameInterface.init()
gameMapPanel:setKeepAspectRatio(true) gameMapPanel:setKeepAspectRatio(true)
gameMapPanel:setVisibleDimension({ width = 15, height = 11 }) gameMapPanel:setVisibleDimension({ width = 15, height = 11 })
end end
end) end, gameRootPanel)
if g_game.isOnline() then if g_game.isOnline() then
GameInterface.show() show()
end end
end end
function GameInterface.terminate() function terminate()
disconnect(g_game, { onGameStart = GameInterface.show, disconnect(g_game, { onGameStart = show,
onGameEnd = GameInterface.hide }) onGameEnd = hide })
disconnect(gameLeftPanel, { onVisibilityChange = onLeftPanelVisibilityChange }) disconnect(gameLeftPanel, { onVisibilityChange = onLeftPanelVisibilityChange })
logoutButton:destroy() logoutButton:destroy()
logoutButton = nil
gameRootPanel:destroy() gameRootPanel:destroy()
gameRootPanel = nil
gameMapPanel = nil
gameRightPanel = nil
gameLeftPanel = nil
gameBottomPanel = nil
mouseGrabberWidget = nil
countWindow = nil
logoutWindow = nil
exitWindow = nil
GameInterface = nil
end end
function GameInterface.show() function show()
connect(g_app, { onClose = GameInterface.tryExit }) connect(g_app, { onClose = tryExit })
logoutButton:show() logoutButton:show()
Background.hide() Background.hide()
gameRootPanel:show() gameRootPanel:show()
@ -116,8 +94,8 @@ function GameInterface.show()
gameMapPanel:followCreature(g_game.getLocalPlayer()) gameMapPanel:followCreature(g_game.getLocalPlayer())
end end
function GameInterface.hide() function hide()
disconnect(g_app, { onClose = GameInterface.tryExit }) disconnect(g_app, { onClose = tryExit })
if logoutWindow then if logoutWindow then
logoutWindow:destroy() logoutWindow:destroy()
logoutWindow = nil logoutWindow = nil
@ -135,7 +113,7 @@ function GameInterface.hide()
Background.show() Background.show()
end end
function GameInterface.exit() function exit()
if g_game.isOnline() then if g_game.isOnline() then
g_game.forceLogout() g_game.forceLogout()
scheduleEvent(exit, 10) scheduleEvent(exit, 10)
@ -143,7 +121,7 @@ function GameInterface.exit()
end end
end end
function GameInterface.tryExit() function tryExit()
if exitWindow then if exitWindow then
return true return true
end end
@ -153,10 +131,10 @@ function GameInterface.tryExit()
local cancelButton = exitWindow:getChildById('buttonCancel') local cancelButton = exitWindow:getChildById('buttonCancel')
local exitFunc = function() local exitFunc = function()
GameInterface.exit() exit()
end end
local logoutFunc = function() local logoutFunc = function()
GameInterface.logout() logout()
logButton:getParent():destroy() logButton:getParent():destroy()
exitWindow = nil exitWindow = nil
end end
@ -174,14 +152,14 @@ function GameInterface.tryExit()
return true -- signal closing return true -- signal closing
end end
function GameInterface.logout() function logout()
if g_game.isOnline() then if g_game.isOnline() then
g_game.safeLogout() g_game.safeLogout()
return true return true
end end
end end
function GameInterface.tryLogout() function tryLogout()
if logoutWindow then if logoutWindow then
return return
end end
@ -190,7 +168,7 @@ function GameInterface.tryLogout()
local noButton = logoutWindow:getChildById('buttonNo') local noButton = logoutWindow:getChildById('buttonNo')
local logoutFunc = function() local logoutFunc = function()
GameInterface.logout() logout()
yesButton:getParent():destroy() yesButton:getParent():destroy()
logoutWindow = nil logoutWindow = nil
end end
@ -206,60 +184,60 @@ function GameInterface.tryLogout()
noButton.onClick = cancelFunc noButton.onClick = cancelFunc
end end
function GameInterface.onMouseGrabberRelease(self, mousePosition, mouseButton) function onMouseGrabberRelease(self, mousePosition, mouseButton)
if GameInterface.selectedThing == nil then return false end if selectedThing == nil then return false end
if mouseButton == MouseLeftButton then if mouseButton == MouseLeftButton then
local clickedWidget = gameRootPanel:recursiveGetChildByPos(mousePosition, false) local clickedWidget = gameRootPanel:recursiveGetChildByPos(mousePosition, false)
if clickedWidget then if clickedWidget then
if GameInterface.selectedType == 'use' then if selectedType == 'use' then
GameInterface.onUseWith(clickedWidget, mousePosition) onUseWith(clickedWidget, mousePosition)
elseif GameInterface.selectedType == 'trade' then elseif selectedType == 'trade' then
GameInterface.onTradeWith(clickedWidget, mousePosition) onTradeWith(clickedWidget, mousePosition)
end end
end end
end end
GameInterface.selectedThing = nil selectedThing = nil
g_mouse.restoreCursor() g_mouse.restoreCursor()
self:ungrabMouse() self:ungrabMouse()
return true return true
end end
function GameInterface.onUseWith(clickedWidget, mousePosition) function onUseWith(clickedWidget, mousePosition)
if clickedWidget:getClassName() == 'UIMap' then if clickedWidget:getClassName() == 'UIMap' then
local tile = clickedWidget:getTile(mousePosition) local tile = clickedWidget:getTile(mousePosition)
if tile then if tile then
g_game.useWith(GameInterface.selectedThing, tile:getTopMultiUseThing()) g_game.useWith(selectedThing, tile:getTopMultiUseThing())
elseif clickedWidget:getClassName() == 'UIItem' and not clickedWidget:isVirtual() then elseif clickedWidget:getClassName() == 'UIItem' and not clickedWidget:isVirtual() then
g_game.useWith(GameInterface.selectedThing, clickedWidget:getItem()) g_game.useWith(selectedThing, clickedWidget:getItem())
end end
end end
end end
function GameInterface.onTradeWith(clickedWidget, mousePosition) function onTradeWith(clickedWidget, mousePosition)
if clickedWidget:getClassName() == 'UIMap' then if clickedWidget:getClassName() == 'UIMap' then
local tile = clickedWidget:getTile(mousePosition) local tile = clickedWidget:getTile(mousePosition)
if tile then if tile then
g_game.requestTrade(GameInterface.selectedThing, tile:getTopCreature()) g_game.requestTrade(selectedThing, tile:getTopCreature())
end end
end end
end end
function GameInterface.startUseWith(thing) function startUseWith(thing)
GameInterface.selectedType = 'use' selectedType = 'use'
GameInterface.selectedThing = thing selectedThing = thing
mouseGrabberWidget:grabMouse() mouseGrabberWidget:grabMouse()
g_mouse.setTargetCursor() g_mouse.setTargetCursor()
end end
function GameInterface.startTradeWith(thing) function startTradeWith(thing)
GameInterface.selectedType = 'trade' selectedType = 'trade'
GameInterface.selectedThing = thing selectedThing = thing
mouseGrabberWidget:grabMouse() mouseGrabberWidget:grabMouse()
g_mouse.setTargetCursor() g_mouse.setTargetCursor()
end end
function GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatureThing) function createThingMenu(menuPosition, lookThing, useThing, creatureThing)
local menu = g_ui.createWidget('PopupMenu') local menu = g_ui.createWidget('PopupMenu')
if lookThing then if lookThing then
@ -276,7 +254,7 @@ function GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatu
end end
else else
if useThing:isMultiUse() then if useThing:isMultiUse() then
menu:addOption(tr('Use with ...'), function() GameInterface.startUseWith(useThing) end) menu:addOption(tr('Use with ...'), function() startUseWith(useThing) end)
else else
menu:addOption(tr('Use'), function() g_game.use(useThing) end) menu:addOption(tr('Use'), function() g_game.use(useThing) end)
end end
@ -290,7 +268,7 @@ function GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatu
if lookThing and not lookThing:asCreature() and not lookThing:isNotMoveable() and lookThing:isPickupable() then if lookThing and not lookThing:asCreature() and not lookThing:isNotMoveable() and lookThing:isPickupable() then
menu:addSeparator() menu:addSeparator()
menu:addOption(tr('Trade with ...'), function() GameInterface.startTradeWith(lookThing) end) menu:addOption(tr('Trade with ...'), function() startTradeWith(lookThing) end)
end end
if lookThing then if lookThing then
@ -336,7 +314,7 @@ function GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatu
menu:addSeparator() menu:addSeparator()
local creatureName = creatureThing:getName() local creatureName = creatureThing:getName()
menu:addOption(tr('Message to %s', creatureName), function() g_game.openPrivateChannel(creatureName) end) menu:addOption(tr('Message to %s', creatureName), function() g_game.openPrivateChannel(creatureName) end)
if Console.getOwnPrivateTab() then if modules.game_console.getOwnPrivateTab() then
menu:addOption(tr('Invite to private chat'), function() g_game.inviteToOwnChannel(creatureName) end) menu:addOption(tr('Invite to private chat'), function() g_game.inviteToOwnChannel(creatureName) end)
menu:addOption(tr('Exclude from private chat'), function() g_game.excludeFromOwnChannel(creatureName) end) -- [TODO] must be removed after message's popup labels been implemented menu:addOption(tr('Exclude from private chat'), function() g_game.excludeFromOwnChannel(creatureName) end) -- [TODO] must be removed after message's popup labels been implemented
end end
@ -383,12 +361,12 @@ function GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatu
menu:display(menuPosition) menu:display(menuPosition)
end end
function GameInterface.processMouseAction(menuPosition, mouseButton, autoWalkPos, lookThing, useThing, creatureThing, multiUseThing) function processMouseAction(menuPosition, mouseButton, autoWalkPos, lookThing, useThing, creatureThing, multiUseThing)
local keyboardModifiers = g_keyboard.getModifiers() local keyboardModifiers = g_keyboard.getModifiers()
if not Options.getOption('classicControl') then if not Options.getOption('classicControl') then
if keyboardModifiers == KeyboardNoModifier and mouseButton == MouseRightButton then if keyboardModifiers == KeyboardNoModifier and mouseButton == MouseRightButton then
GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatureThing) createThingMenu(menuPosition, lookThing, useThing, creatureThing)
return true return true
elseif lookThing and keyboardModifiers == KeyboardShiftModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then elseif lookThing and keyboardModifiers == KeyboardShiftModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then
g_game.look(lookThing) g_game.look(lookThing)
@ -403,7 +381,7 @@ function GameInterface.processMouseAction(menuPosition, mouseButton, autoWalkPos
return true return true
end end
elseif useThing:isMultiUse() then elseif useThing:isMultiUse() then
GameInterface.startUseWith(useThing) startUseWith(useThing)
return true return true
else else
g_game.use(useThing) g_game.use(useThing)
@ -429,7 +407,7 @@ function GameInterface.processMouseAction(menuPosition, mouseButton, autoWalkPos
return true return true
end end
elseif multiUseThing:isMultiUse() then elseif multiUseThing:isMultiUse() then
GameInterface.startUseWith(useThing) startUseWith(useThing)
return true return true
else else
g_game.use(multiUseThing) g_game.use(multiUseThing)
@ -442,7 +420,7 @@ function GameInterface.processMouseAction(menuPosition, mouseButton, autoWalkPos
g_game.look(lookThing) g_game.look(lookThing)
return true return true
elseif useThing and keyboardModifiers == KeyboardCtrlModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then elseif useThing and keyboardModifiers == KeyboardCtrlModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then
GameInterface.createThingMenu(menuPosition, lookThing, useThing, creatureThing) createThingMenu(menuPosition, lookThing, useThing, creatureThing)
return true return true
elseif creatureThing and keyboardModifiers == KeyboardAltModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then elseif creatureThing and keyboardModifiers == KeyboardAltModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then
g_game.attack(creatureThing) g_game.attack(creatureThing)
@ -453,7 +431,7 @@ function GameInterface.processMouseAction(menuPosition, mouseButton, autoWalkPos
if autoWalkPos and keyboardModifiers == KeyboardNoModifier and mouseButton == MouseLeftButton then if autoWalkPos and keyboardModifiers == KeyboardNoModifier and mouseButton == MouseLeftButton then
local dirs = g_map.findPath(g_game.getLocalPlayer():getPosition(), autoWalkPos, 127) local dirs = g_map.findPath(g_game.getLocalPlayer():getPosition(), autoWalkPos, 127)
if #dirs == 0 then if #dirs == 0 then
TextMessage.displayStatus(tr('There is no way.')) modules.game_textmessage.displayStatus(tr('There is no way.'))
return true return true
end end
g_game.autoWalk(dirs) g_game.autoWalk(dirs)
@ -463,7 +441,7 @@ function GameInterface.processMouseAction(menuPosition, mouseButton, autoWalkPos
return false return false
end end
function GameInterface.moveStackableItem(item, toPos) function moveStackableItem(item, toPos)
if(countWindow) then if(countWindow) then
return return
end end
@ -507,22 +485,32 @@ function GameInterface.moveStackableItem(item, toPos)
cancelButton.onClick = cancelFunc cancelButton.onClick = cancelFunc
end end
function GameInterface.getRootPanel() function getRootPanel()
return gameRootPanel return gameRootPanel
end end
function GameInterface.getMapPanel() function getMapPanel()
return gameMapPanel return gameMapPanel
end end
function GameInterface.getRightPanel() function getRightPanel()
return gameRightPanel return gameRightPanel
end end
function GameInterface.getLeftPanel() function getLeftPanel()
return gameLeftPanel return gameLeftPanel
end end
function GameInterface.getBottomPanel() function getBottomPanel()
return gameBottomPanel return gameBottomPanel
end end
local function onLeftPanelVisibilityChange(leftPanel, visible)
if not visible then
local children = leftPanel:getChildren()
for i=1,#children do
children[i]:setParent(gameRightPanel)
end
end
end

@ -3,7 +3,8 @@ Module
description: Create the game interface, where the ingame stuff starts description: Create the game interface, where the ingame stuff starts
author: OTClient team author: OTClient team
website: www.otclient.info website: www.otclient.info
sandboxed: true
scripts: [ widgets/uigamemap.lua, widgets/uiitem.lua, gameinterface.lua ]
load-later: load-later:
- game_hotkeys - game_hotkeys
- game_questlog - game_questlog
@ -27,14 +28,5 @@ Module
- game_playerdeath - game_playerdeath
- game_playermount - game_playermount
- game_market - game_market
@onLoad: init()
@onLoad: | @onUnload: terminate()
dofile 'widgets/uigamemap'
dofile 'widgets/uiitem'
dofile 'gameinterface'
GameInterface.init()
@onUnload: |
GameInterface.terminate()

@ -39,7 +39,7 @@ function UIGameMap:onDrop(widget, mousePos)
if thingPos.x == toPos.x and thingPos.y == toPos.y and thingPos.z == toPos.z then return false end if thingPos.x == toPos.x and thingPos.y == toPos.y and thingPos.z == toPos.z then return false end
if thing:asItem() and thing:getCount() > 1 then if thing:asItem() and thing:getCount() > 1 then
GameInterface.moveStackableItem(thing, toPos) modules.game_interface.moveStackableItem(thing, toPos)
else else
g_game.move(thing, toPos, 1) g_game.move(thing, toPos, 1)
end end
@ -74,7 +74,7 @@ function UIGameMap:onMouseRelease(mousePosition, mouseButton)
local creatureThing = tile:getTopCreature() local creatureThing = tile:getTopCreature()
local multiUseThing = tile:getTopMultiUseThing() local multiUseThing = tile:getTopMultiUseThing()
local ret = GameInterface.processMouseAction(mousePosition, mouseButton, autoWalkPos, lookThing, useThing, creatureThing, multiUseThing) local ret = modules.game_interface.processMouseAction(mousePosition, mouseButton, autoWalkPos, lookThing, useThing, creatureThing, multiUseThing)
if ret then if ret then
self.cancelNextRelease = true self.cancelNextRelease = true
end end

@ -30,7 +30,7 @@ function UIItem:onDrop(widget, mousePos)
if itemPos.x == toPos.x and itemPos.y == toPos.y and itemPos.z == toPos.z then return false end if itemPos.x == toPos.x and itemPos.y == toPos.y and itemPos.z == toPos.z then return false end
if item:getCount() > 1 then if item:getCount() > 1 then
GameInterface.moveStackableItem(item, toPos) modules.game_interface.moveStackableItem(item, toPos)
else else
g_game.move(item, toPos, 1) g_game.move(item, toPos, 1)
end end
@ -73,7 +73,7 @@ function UIItem:onMouseRelease(mousePosition, mouseButton)
g_game.look(item) g_game.look(item)
self.cancelNextRelease = true self.cancelNextRelease = true
return true return true
elseif GameInterface.processMouseAction(mousePosition, mouseButton, nil, item, item, nil, item) then elseif modules.game_interface.processMouseAction(mousePosition, mouseButton, nil, item, item, nil, item) then
return true return true
end end
return false return false

@ -1,6 +1,3 @@
Inventory = {}
-- public variables
InventorySlotStyles = { InventorySlotStyles = {
[InventorySlotHead] = "HeadSlot", [InventorySlotHead] = "HeadSlot",
[InventorySlotNeck] = "NeckSlot", [InventorySlotNeck] = "NeckSlot",
@ -14,54 +11,47 @@ InventorySlotStyles = {
[InventorySlotAmmo] = "AmmoSlot" [InventorySlotAmmo] = "AmmoSlot"
} }
-- private variables inventoryWindow = nil
local inventoryWindow inventoryPanel = nil
local inventoryPanel inventoryButton = nil
local inventoryButton
-- public functions function init()
function Inventory.init() connect(LocalPlayer, { onInventoryChange = onInventoryChange })
connect(LocalPlayer, { onInventoryChange = Inventory.onInventoryChange }) connect(g_game, { onGameStart = refresh })
connect(g_game, { onGameStart = Inventory.refresh })
g_keyboard.bindKeyDown('Ctrl+I', Inventory.toggle) g_keyboard.bindKeyDown('Ctrl+I', toggle)
inventoryWindow = g_ui.loadUI('inventory.otui', GameInterface.getRightPanel()) inventoryWindow = g_ui.loadUI('inventory.otui', modules.game_interface.getRightPanel())
inventoryWindow:disableResize() inventoryWindow:disableResize()
inventoryPanel = inventoryWindow:getChildById('contentsPanel') inventoryPanel = inventoryWindow:getChildById('contentsPanel')
inventoryButton = TopMenu.addRightGameToggleButton('inventoryButton', tr('Inventory') .. ' (Ctrl+I)', 'inventory.png', Inventory.toggle) inventoryButton = TopMenu.addRightGameToggleButton('inventoryButton', tr('Inventory') .. ' (Ctrl+I)', 'inventory.png', toggle)
inventoryButton:setOn(true) inventoryButton:setOn(true)
Inventory.refresh() refresh()
end end
function Inventory.terminate() function terminate()
disconnect(LocalPlayer, { onInventoryChange = Inventory.onInventoryChange }) disconnect(LocalPlayer, { onInventoryChange = onInventoryChange })
disconnect(g_game, { onGameStart = Inventory.refresh }) disconnect(g_game, { onGameStart = refresh })
g_keyboard.unbindKeyDown('Ctrl+I') g_keyboard.unbindKeyDown('Ctrl+I')
inventoryWindow:destroy() inventoryWindow:destroy()
inventoryButton:destroy() inventoryButton:destroy()
inventoryWindow = nil
inventoryButton = nil
inventoryPanel = nil
Inventory = nil
end end
function Inventory.refresh() function refresh()
local player = g_game.getLocalPlayer() local player = g_game.getLocalPlayer()
for i=InventorySlotFirst,InventorySlotLast do for i=InventorySlotFirst,InventorySlotLast do
if player then if player then
Inventory.onInventoryChange(player, i, player:getInventoryItem(i)) onInventoryChange(player, i, player:getInventoryItem(i))
else else
Inventory.onInventoryChange(player, i, nil) onInventoryChange(player, i, nil)
end end
end end
end end
function Inventory.toggle() function toggle()
if inventoryButton:isOn() then if inventoryButton:isOn() then
inventoryWindow:close() inventoryWindow:close()
inventoryButton:setOn(false) inventoryButton:setOn(false)
@ -71,12 +61,12 @@ function Inventory.toggle()
end end
end end
function Inventory.onMiniWindowClose() function onMiniWindowClose()
inventoryButton:setOn(false) inventoryButton:setOn(false)
end end
-- hooked events -- hooked events
function Inventory.onInventoryChange(player, slot, item, oldItem) function onInventoryChange(player, slot, item, oldItem)
local itemWidget = inventoryPanel:getChildById('slot' .. slot) local itemWidget = inventoryPanel:getChildById('slot' .. slot)
if(item) then if(item) then
itemWidget:setStyle('Item') itemWidget:setStyle('Item')

@ -3,14 +3,7 @@ Module
description: View local player equipments window description: View local player equipments window
author: baxnie, edubart, BeniS author: baxnie, edubart, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ inventory.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'inventory'
Inventory.init()
@onUnload: |
Inventory.terminate()

@ -56,7 +56,7 @@ MiniWindow
!text: tr('Inventory') !text: tr('Inventory')
icon: inventory.png icon: inventory.png
height: 95 height: 95
@onClose: Inventory.onMiniWindowClose() @onClose: onMiniWindowClose()
&save: true &save: true
MiniWindowContents MiniWindowContents

@ -1,64 +1,33 @@
Minimap = {} DEFAULT_ZOOM = 60
MAX_FLOOR_UP = 0
MAX_FLOOR_DOWN = 15
-- public variables G.minimapFirstLoad = true
minimapFirstLoad = true
-- private variables navigating = false
local minimapWidget minimapWidget = nil
local minimapButton minimapButton = nil
local minimapWindow minimapWindow = nil
local DEFAULT_ZOOM = 60
local MAX_FLOOR_UP = 0
local MAX_FLOOR_DOWN = 15
local navigating = false
-- private functions
function onMinimapMouseRelease(self, mousePosition, mouseButton)
if navigating then
navigating = false
return
end
local tile = self:getTile(mousePosition)
if tile and mouseButton == MouseLeftButton and self:isPressed() then
local dirs = g_map.findPath(g_game.getLocalPlayer():getPosition(), tile:getPosition(), 127)
if #dirs == 0 then
TextMessage.displayStatus(tr('There is no way.'))
return true
end
g_game.autoWalk(dirs)
return true
end
return false
end
function onMinimapMouseWheel(self, mousePos, direction)
if direction == MouseWheelUp then
self:zoomIn()
else
self:zoomOut()
end
end
--[[ --[[
Known Issue (TODO): Known Issue (TODO):
If you move the minimap compass directions and If you move the minimap compass directions and
you change floor it will not update the minimap. you change floor it will not update the minimap.
]] ]]
-- public functions function init()
function Minimap.init() connect(g_game, { onGameStart = reset,
connect(g_game, { onGameStart = Minimap.reset, onForceWalk = center })
onForceWalk = Minimap.center })
g_keyboard.bindKeyDown('Ctrl+M', Minimap.toggle) g_keyboard.bindKeyDown('Ctrl+M', toggle)
minimapButton = TopMenu.addRightGameToggleButton('minimapButton', tr('Minimap') .. ' (Ctrl+M)', 'minimap.png', Minimap.toggle) minimapButton = TopMenu.addRightGameToggleButton('minimapButton', tr('Minimap') .. ' (Ctrl+M)', 'minimap.png', toggle)
minimapButton:setOn(true) minimapButton:setOn(true)
minimapWindow = g_ui.loadUI('minimap.otui', GameInterface.getRightPanel()) minimapWindow = g_ui.loadUI('minimap.otui', modules.game_interface.getRightPanel())
minimapWidget = minimapWindow:recursiveGetChildById('minimap') minimapWidget = minimapWindow:recursiveGetChildById('minimap')
g_mouse.bindAutoPress(minimapWidget, Minimap.compassClick, nil, MouseRightButton) g_mouse.bindAutoPress(minimapWidget, compassClick, nil, MouseRightButton)
g_mouse.bindAutoPress(minimapWidget, Minimap.compassClick, nil, MouseLeftButton) g_mouse.bindAutoPress(minimapWidget, compassClick, nil, MouseLeftButton)
minimapWidget:setAutoViewMode(false) minimapWidget:setAutoViewMode(false)
minimapWidget:setViewMode(1) -- mid view minimapWidget:setViewMode(1) -- mid view
minimapWidget:setDrawMinimapColors(true) minimapWidget:setDrawMinimapColors(true)
@ -67,11 +36,11 @@ function Minimap.init()
minimapWidget.onMouseRelease = onMinimapMouseRelease minimapWidget.onMouseRelease = onMinimapMouseRelease
minimapWidget.onMouseWheel = onMinimapMouseWheel minimapWidget.onMouseWheel = onMinimapMouseWheel
Minimap.reset() reset()
-- load only the first time (avoid load/save between reloads) -- load only the first time (avoid load/save between reloads)
if minimapFirstLoad then if G.minimapFirstLoad then
minimapFirstLoad = false G.minimapFirstLoad = false
if g_resources.fileExists('/minimap.otcm') then if g_resources.fileExists('/minimap.otcm') then
if g_game.isOnline() then if g_game.isOnline() then
perror('cannot load minimap while online') perror('cannot load minimap while online')
@ -87,21 +56,17 @@ function Minimap.init()
end end
end end
function Minimap.terminate() function terminate()
disconnect(g_game, { onGameStart = Minimap.reset, disconnect(g_game, { onGameStart = reset,
onForceWalk = Minimap.center }) onForceWalk = center })
g_keyboard.unbindKeyDown('Ctrl+M') g_keyboard.unbindKeyDown('Ctrl+M')
minimapButton:destroy() minimapButton:destroy()
minimapWindow:destroy() minimapWindow:destroy()
minimapWindow = nil
minimapWidget = nil
minimapButton = nil
Minimap = nil
end end
function Minimap.toggle() function toggle()
if minimapButton:isOn() then if minimapButton:isOn() then
minimapWindow:close() minimapWindow:close()
minimapButton:setOn(false) minimapButton:setOn(false)
@ -111,16 +76,24 @@ function Minimap.toggle()
end end
end end
function Minimap.onMiniWindowClose() function isClickInRange(position, fromPosition, toPosition)
minimapButton:setOn(false) return (position.x >= fromPosition.x and position.y >= fromPosition.y and position.x <= toPosition.x and position.y <= toPosition.y)
end end
function Minimap.isClickInRange(position, fromPosition, toPosition) function reset()
return (position.x >= fromPosition.x and position.y >= fromPosition.y and position.x <= toPosition.x and position.y <= toPosition.y) local player = g_game.getLocalPlayer()
if not player then return end
minimapWidget:followCreature(player)
minimapWidget:setZoom(DEFAULT_ZOOM)
end end
-- hooked functions function center()
function Minimap.compassClick(self, mousePos, mouseButton, elapsed) local player = g_game.getLocalPlayer()
if not player then return end
minimapWidget:followCreature(player)
end
function compassClick(self, mousePos, mouseButton, elapsed)
if elapsed < 300 then return end if elapsed < 300 then return end
navigating = true navigating = true
@ -144,7 +117,7 @@ function Minimap.compassClick(self, mousePos, mouseButton, elapsed)
minimapWidget:setCameraPosition(pos) minimapWidget:setCameraPosition(pos)
end end
function Minimap.onButtonClick(id) function onButtonClick(id)
if id == "zoomIn" then if id == "zoomIn" then
minimapWidget:setZoom(math.max(minimapWidget:getMaxZoomIn(), minimapWidget:getZoom()-15)) minimapWidget:setZoom(math.max(minimapWidget:getMaxZoomIn(), minimapWidget:getZoom()-15))
elseif id == "zoomOut" then elseif id == "zoomOut" then
@ -164,16 +137,32 @@ function Minimap.onButtonClick(id)
end end
end end
-- hooked events function onMinimapMouseRelease(self, mousePosition, mouseButton)
function Minimap.reset() if navigating then
local player = g_game.getLocalPlayer() navigating = false
if not player then return end return
minimapWidget:followCreature(player) end
minimapWidget:setZoom(DEFAULT_ZOOM) local tile = self:getTile(mousePosition)
if tile and mouseButton == MouseLeftButton and self:isPressed() then
local dirs = g_map.findPath(g_game.getLocalPlayer():getPosition(), tile:getPosition(), 127)
if #dirs == 0 then
modules.game_textmessage.displayStatus(tr('There is no way.'))
return true
end
g_game.autoWalk(dirs)
return true
end
return false
end end
function Minimap.center() function onMinimapMouseWheel(self, mousePos, direction)
local player = g_game.getLocalPlayer() if direction == MouseWheelUp then
if not player then return end self:zoomIn()
minimapWidget:followCreature(player) else
end self:zoomOut()
end
end
function onMiniWindowClose()
minimapButton:setOn(false)
end

@ -3,13 +3,7 @@ Module
description: Manage minimap description: Manage minimap
author: edubart, BeniS author: edubart, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [minimap.lua]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'minimap'
Minimap.init()
@onUnload: |
Minimap.terminate()

@ -25,7 +25,7 @@ MiniWindow
!text: tr('Minimap') !text: tr('Minimap')
height: 150 height: 150
icon: minimap.png icon: minimap.png
@onClose: Minimap.onMiniWindowClose() @onClose: onMiniWindowClose()
&save: true &save: true
Label Label
@ -51,7 +51,7 @@ MiniWindow
margin-right: 28 margin-right: 28
margin-bottom: 28 margin-bottom: 28
enabled: true enabled: true
@onClick: Minimap.onButtonClick(self:getId()) @onClick: onButtonClick(self:getId())
FloorDownControl FloorDownControl
id: floorDown id: floorDown
@ -60,7 +60,7 @@ MiniWindow
margin-right: 28 margin-right: 28
margin-bottom: 4 margin-bottom: 4
enabled: true enabled: true
@onClick: Minimap.onButtonClick(self:getId()) @onClick: onButtonClick(self:getId())
ZoomInControl ZoomInControl
id: zoomIn id: zoomIn
@ -70,7 +70,7 @@ MiniWindow
margin-right: 4 margin-right: 4
margin-bottom: 28 margin-bottom: 28
enabled: true enabled: true
@onClick: Minimap.onButtonClick(self:getId()) @onClick: onButtonClick(self:getId())
ZoomOutControl ZoomOutControl
id: zoomOut id: zoomOut
@ -81,7 +81,7 @@ MiniWindow
margin-right: 4 margin-right: 4
margin-bottom: 4 margin-bottom: 4
enabled: true enabled: true
@onClick: Minimap.onButtonClick(self:getId()) @onClick: onButtonClick(self:getId())
Button Button
id: reset id: reset
@ -90,5 +90,5 @@ MiniWindow
anchors.left: parent.left anchors.left: parent.left
anchors.top: parent.top anchors.top: parent.top
margin: 4 margin: 4
@onClick: Minimap.center() @onClick: center()

@ -1,44 +1,193 @@
NPCTrade = {} BUY = 1
SELL = 2
-- private variables CURRENCY = 'gold'
local BUY = 1 WEIGHT_UNIT = 'oz'
local SELL = 2 LAST_INVENTORY = 10
local CURRENCY = 'gold'
local WEIGHT_UNIT = 'oz' npcWindow = nil
local LAST_INVENTORY = 10 itemsPanel = nil
radioTabs = nil
local npcWindow radioItems = nil
local itemsPanel searchText = nil
local radioTabs setupPanel = nil
local radioItems quantity = nil
local searchText quantityScroll = nil
local setupPanel nameLabel = nil
local quantity priceLabel = nil
local quantityScroll moneyLabel = nil
local nameLabel weightLabel = nil
local priceLabel capacityLabel = nil
local moneyLabel tradeButton = nil
local weightLabel buyTab = nil
local capacityLabel sellTab = nil
local tradeButton
local buyTab showCapacity = true
local sellTab buyWithBackpack = nil
ignoreCapacity = nil
local showCapacity = true ignoreEquipped = nil
local buyWithBackpack showAllItems = nil
local ignoreCapacity
local ignoreEquipped playerFreeCapacity = nil
local showAllItems playerMoney = nil
tradeItems = {}
local playerFreeCapacity playerItems = nil
local playerMoney selectedItem = nil
local tradeItems = {}
local playerItems function init()
npcWindow = g_ui.displayUI('npctrade.otui')
local selectedItem npcWindow:setVisible(false)
-- private functions itemsPanel = npcWindow:recursiveGetChildById('itemsPanel')
local function clearSelectedItem() searchText = npcWindow:recursiveGetChildById('searchText')
setupPanel = npcWindow:recursiveGetChildById('setupPanel')
quantityLabel = setupPanel:getChildById('quantity')
quantityScroll = setupPanel:getChildById('quantityScroll')
nameLabel = setupPanel:getChildById('name')
priceLabel = setupPanel:getChildById('price')
moneyLabel = setupPanel:getChildById('money')
weightLabel = setupPanel:getChildById('weight')
capacityLabel = setupPanel:getChildById('capacity')
tradeButton = npcWindow:recursiveGetChildById('tradeButton')
buyWithBackpack = npcWindow:recursiveGetChildById('buyWithBackpack')
ignoreCapacity = npcWindow:recursiveGetChildById('ignoreCapacity')
ignoreEquipped = npcWindow:recursiveGetChildById('ignoreEquipped')
showAllItems = npcWindow:recursiveGetChildById('showAllItems')
buyTab = npcWindow:getChildById('buyTab')
sellTab = npcWindow:getChildById('sellTab')
radioTabs = UIRadioGroup.create()
radioTabs:addWidget(buyTab)
radioTabs:addWidget(sellTab)
radioTabs:selectWidget(buyTab)
radioTabs.onSelectionChange = onTradeTypeChange
if g_game.isOnline() then
playerFreeCapacity = g_game.getLocalPlayer():getFreeCapacity()
end
connect(g_game, { onGameEnd = hide,
onOpenNpcTrade = onOpenNpcTrade,
onCloseNpcTrade = onCloseNpcTrade,
onPlayerGoods = onPlayerGoods } )
connect(LocalPlayer, { onFreeCapacityChange = onFreeCapacityChange,
onInventoryChange = onInventoryChange } )
end
function terminate()
npcWindow:destroy()
disconnect(g_game, { onGameEnd = hide,
onOpenNpcTrade = onOpenNpcTrade,
onCloseNpcTrade = onCloseNpcTrade,
onPlayerGoods = onPlayerGoods } )
disconnect(LocalPlayer, { onFreeCapacityChange = onFreeCapacityChange,
onInventoryChange = onInventoryChange } )
end
function show()
if g_game.isOnline() then
if #tradeItems[BUY] > 0 then
radioTabs:selectWidget(buyTab)
else
radioTabs:selectWidget(sellTab)
end
npcWindow:show()
npcWindow:raise()
npcWindow:focus()
end
end
function hide()
npcWindow:hide()
end
function onItemBoxChecked(widget)
if widget:isChecked() then
local item = widget.item
selectedItem = item
refreshItem(item)
tradeButton:enable()
end
end
function onQuantityValueChange(quantity)
if quantityLabel and selectedItem then
quantityLabel:setText(quantity)
weightLabel:setText(string.format('%.2f', selectedItem.weight*quantity) .. ' ' .. WEIGHT_UNIT)
priceLabel:setText(getItemPrice(selectedItem) .. ' ' .. CURRENCY)
end
end
function onTradeTypeChange(radioTabs, selected, deselected)
tradeButton:setText(selected:getText())
selected:setOn(true)
deselected:setOn(false)
local currentTradeType = getCurrentTradeType()
buyWithBackpack:setVisible(currentTradeType == BUY)
ignoreCapacity:setVisible(currentTradeType == BUY)
ignoreEquipped:setVisible(currentTradeType == SELL)
showAllItems:setVisible(currentTradeType == SELL)
refreshTradeItems()
refreshPlayerGoods()
end
function onTradeClick()
if getCurrentTradeType() == BUY then
g_game.buyItem(selectedItem.ptr, quantityScroll:getValue(), ignoreCapacity:isChecked(), buyWithBackpack:isChecked())
else
g_game.sellItem(selectedItem.ptr, quantityScroll:getValue(), ignoreEquipped:isChecked())
end
end
function onSearchTextChange()
refreshPlayerGoods()
end
function itemPopup(self, mousePosition, mouseButton)
if mouseButton == MouseRightButton then
local menu = g_ui.createWidget('PopupMenu')
menu:addOption(tr('Look'), function() return g_game.inspectNpcTrade(self:getItem()) end)
menu:display(mousePosition)
return true
end
return false
end
function onBuyWithBackpackChange()
if selectedItem then
refreshItem(selectedItem)
end
end
function onIgnoreCapacityChange()
refreshPlayerGoods()
end
function onIgnoreEquippedChange()
refreshPlayerGoods()
end
function onShowAllItemsChange()
refreshPlayerGoods()
end
function setCurrency(currency)
CURRENCY = currency
end
function showCapacity(state)
showCapacity = state
end
function clearSelectedItem()
nameLabel:clearText() nameLabel:clearText()
weightLabel:clearText() weightLabel:clearText()
priceLabel:clearText() priceLabel:clearText()
@ -51,7 +200,7 @@ local function clearSelectedItem()
end end
end end
local function getCurrentTradeType() function getCurrentTradeType()
if tradeButton:getText() == tr('Buy') then if tradeButton:getText() == tr('Buy') then
return BUY return BUY
else else
@ -59,7 +208,7 @@ local function getCurrentTradeType()
end end
end end
local function getItemPrice(item) function getItemPrice(item)
if getCurrentTradeType() == BUY then if getCurrentTradeType() == BUY then
if buyWithBackpack:isChecked() then if buyWithBackpack:isChecked() then
if item.ptr:isStackable() then if item.ptr:isStackable() then
@ -72,7 +221,7 @@ local function getItemPrice(item)
return item.price*quantityScroll:getValue() return item.price*quantityScroll:getValue()
end end
local function getSellQuantity(item) function getSellQuantity(item)
if not playerItems[item.ptr:getId()] then if not playerItems[item.ptr:getId()] then
return 0 return 0
end end
@ -90,7 +239,7 @@ local function getSellQuantity(item)
return playerItems[item.ptr:getId()] - removeAmount return playerItems[item.ptr:getId()] - removeAmount
end end
local function canTradeItem(item) function canTradeItem(item)
if getCurrentTradeType() == BUY then if getCurrentTradeType() == BUY then
return (ignoreCapacity:isChecked() or (not ignoreCapacity:isChecked() and playerFreeCapacity >= item.weight)) and playerMoney >= getItemPrice(item) return (ignoreCapacity:isChecked() or (not ignoreCapacity:isChecked() and playerFreeCapacity >= item.weight)) and playerMoney >= getItemPrice(item)
else else
@ -98,7 +247,7 @@ local function canTradeItem(item)
end end
end end
local function refreshItem(item) function refreshItem(item)
nameLabel:setText(item.name) nameLabel:setText(item.name)
weightLabel:setText(string.format('%.2f', item.weight) .. ' ' .. WEIGHT_UNIT) weightLabel:setText(string.format('%.2f', item.weight) .. ' ' .. WEIGHT_UNIT)
priceLabel:setText(getItemPrice(item) .. ' ' .. CURRENCY) priceLabel:setText(getItemPrice(item) .. ' ' .. CURRENCY)
@ -130,7 +279,7 @@ local function refreshItem(item)
setupPanel:enable() setupPanel:enable()
end end
local function refreshTradeItems() function refreshTradeItems()
local layout = itemsPanel:getLayout() local layout = itemsPanel:getLayout()
layout:disableUpdates() layout:disableUpdates()
@ -163,7 +312,7 @@ local function refreshTradeItems()
local itemWidget = itemBox:getChildById('item') local itemWidget = itemBox:getChildById('item')
itemWidget:setItem(item.ptr) itemWidget:setItem(item.ptr)
itemWidget.onMouseRelease = NPCTrade.itemPopup itemWidget.onMouseRelease = itemPopup
radioItems:addWidget(itemBox) radioItems:addWidget(itemBox)
end end
@ -172,7 +321,7 @@ local function refreshTradeItems()
layout:update() layout:update()
end end
local function refreshPlayerGoods() function refreshPlayerGoods()
moneyLabel:setText(playerMoney .. ' ' .. CURRENCY) moneyLabel:setText(playerMoney .. ' ' .. CURRENCY)
capacityLabel:setText(string.format('%.2f', playerFreeCapacity) .. ' ' .. WEIGHT_UNIT) capacityLabel:setText(string.format('%.2f', playerFreeCapacity) .. ' ' .. WEIGHT_UNIT)
@ -206,8 +355,7 @@ local function refreshPlayerGoods()
end end
end end
-- hooked functions function onOpenNpcTrade(items)
local function onOpenNpcTrade(items)
tradeItems[BUY] = {} tradeItems[BUY] = {}
tradeItems[SELL] = {} tradeItems[SELL] = {}
@ -229,14 +377,14 @@ local function onOpenNpcTrade(items)
end end
refreshTradeItems() refreshTradeItems()
addEvent(NPCTrade.show) -- player goods has not been parsed yet addEvent(show) -- player goods has not been parsed yet
end end
local function onCloseNpcTrade() function onCloseNpcTrade()
NPCTrade.hide() hide()
end end
local function onPlayerGoods(money, items) function onPlayerGoods(money, items)
playerMoney = money playerMoney = money
playerItems = {} playerItems = {}
@ -252,7 +400,7 @@ local function onPlayerGoods(money, items)
refreshPlayerGoods() refreshPlayerGoods()
end end
local function onFreeCapacityChange(localPlayer, freeCapacity, oldFreeCapacity) function onFreeCapacityChange(localPlayer, freeCapacity, oldFreeCapacity)
playerFreeCapacity = freeCapacity playerFreeCapacity = freeCapacity
if npcWindow:isVisible() then if npcWindow:isVisible() then
@ -260,186 +408,9 @@ local function onFreeCapacityChange(localPlayer, freeCapacity, oldFreeCapacity)
end end
end end
local function onInventoryChange(inventory, item, oldeItem) function onInventoryChange(inventory, item, oldeItem)
if selectedItem then if selectedItem then
refreshItem(selectedItem) refreshItem(selectedItem)
end end
end end
-- public functions
function NPCTrade.init()
npcWindow = g_ui.displayUI('npctrade.otui')
npcWindow:setVisible(false)
itemsPanel = npcWindow:recursiveGetChildById('itemsPanel')
searchText = npcWindow:recursiveGetChildById('searchText')
setupPanel = npcWindow:recursiveGetChildById('setupPanel')
quantityLabel = setupPanel:getChildById('quantity')
quantityScroll = setupPanel:getChildById('quantityScroll')
nameLabel = setupPanel:getChildById('name')
priceLabel = setupPanel:getChildById('price')
moneyLabel = setupPanel:getChildById('money')
weightLabel = setupPanel:getChildById('weight')
capacityLabel = setupPanel:getChildById('capacity')
tradeButton = npcWindow:recursiveGetChildById('tradeButton')
buyWithBackpack = npcWindow:recursiveGetChildById('buyWithBackpack')
ignoreCapacity = npcWindow:recursiveGetChildById('ignoreCapacity')
ignoreEquipped = npcWindow:recursiveGetChildById('ignoreEquipped')
showAllItems = npcWindow:recursiveGetChildById('showAllItems')
buyTab = npcWindow:getChildById('buyTab')
sellTab = npcWindow:getChildById('sellTab')
radioTabs = UIRadioGroup.create()
radioTabs:addWidget(buyTab)
radioTabs:addWidget(sellTab)
radioTabs:selectWidget(buyTab)
radioTabs.onSelectionChange = NPCTrade.onTradeTypeChange
if g_game.isOnline() then -- event wont be sent again when reloading modules
playerFreeCapacity = g_game.getLocalPlayer():getFreeCapacity()
end
connect(g_game, { onGameEnd = NPCTrade.hide,
onOpenNpcTrade = onOpenNpcTrade,
onCloseNpcTrade = onCloseNpcTrade,
onPlayerGoods = onPlayerGoods } )
connect(LocalPlayer, { onFreeCapacityChange = onFreeCapacityChange,
onInventoryChange = onInventoryChange } )
end
function NPCTrade.terminate()
--radioTabs:destroy()
radioTabs = nil
npcWindow:destroy()
npcWindow = nil
itemsPanel = nil
buyButton = nil
sellButton = nil
searchText = nil
buyTab = nil
sellTab = nil
setupPanel = nil
quantityLabel = nil
quantityScroll = nil
nameLabel = nil
priceLabel = nil
moneyLabel = nil
weightLabel = nil
capacityLabel = nil
offerSelected = nil
tradeButton = nil
disconnect(g_game, { onGameEnd = NPCTrade.hide,
onOpenNpcTrade = onOpenNpcTrade,
onCloseNpcTrade = onCloseNpcTrade,
onPlayerGoods = onPlayerGoods } )
disconnect(LocalPlayer, { onFreeCapacityChange = onFreeCapacityChange,
onInventoryChange = onInventoryChange } )
NPCTrade = nil
end
function NPCTrade.show()
if g_game.isOnline() then
if #tradeItems[BUY] > 0 then
radioTabs:selectWidget(buyTab)
else
radioTabs:selectWidget(sellTab)
end
npcWindow:show()
npcWindow:raise()
npcWindow:focus()
end
end
function NPCTrade.hide()
npcWindow:hide()
end
function NPCTrade.onItemBoxChecked(widget)
if widget:isChecked() then
local item = widget.item
selectedItem = item
refreshItem(item)
tradeButton:enable()
end
end
function NPCTrade.onQuantityValueChange(quantity)
if quantityLabel and selectedItem then
quantityLabel:setText(quantity)
weightLabel:setText(string.format('%.2f', selectedItem.weight*quantity) .. ' ' .. WEIGHT_UNIT)
priceLabel:setText(getItemPrice(selectedItem) .. ' ' .. CURRENCY)
end
end
function NPCTrade.onTradeTypeChange(radioTabs, selected, deselected)
tradeButton:setText(selected:getText())
selected:setOn(true)
deselected:setOn(false)
local currentTradeType = getCurrentTradeType()
buyWithBackpack:setVisible(currentTradeType == BUY)
ignoreCapacity:setVisible(currentTradeType == BUY)
ignoreEquipped:setVisible(currentTradeType == SELL)
showAllItems:setVisible(currentTradeType == SELL)
refreshTradeItems()
refreshPlayerGoods()
end
function NPCTrade.onTradeClick()
if getCurrentTradeType() == BUY then
g_game.buyItem(selectedItem.ptr, quantityScroll:getValue(), ignoreCapacity:isChecked(), buyWithBackpack:isChecked())
else
g_game.sellItem(selectedItem.ptr, quantityScroll:getValue(), ignoreEquipped:isChecked())
end
end
function NPCTrade.onSearchTextChange()
refreshPlayerGoods()
end
function NPCTrade.itemPopup(self, mousePosition, mouseButton)
if mouseButton == MouseRightButton then
local menu = g_ui.createWidget('PopupMenu')
menu:addOption(tr('Look'), function() return g_game.inspectNpcTrade(self:getItem()) end)
menu:display(mousePosition)
return true
end
return false
end
function NPCTrade.onBuyWithBackpackChange()
if selectedItem then
refreshItem(selectedItem)
end
end
function NPCTrade.onIgnoreCapacityChange()
refreshPlayerGoods()
end
function NPCTrade.onIgnoreEquippedChange()
refreshPlayerGoods()
end
function NPCTrade.onShowAllItemsChange()
refreshPlayerGoods()
end
function NPCTrade.setCurrency(currency)
CURRENCY = currency
end
function NPCTrade.showCapacity(state)
showCapacity = state
end

@ -3,13 +3,7 @@ Module
description: NPC trade interface description: NPC trade interface
author: andrefaramir, baxnie author: andrefaramir, baxnie
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ npctrade.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'npctrade'
NPCTrade.init()
@onUnload: |
NPCTrade.terminate()

@ -1,7 +1,4 @@
Outfit = {} ADDON_SETS = {
-- private variables
local addonSets = {
[1] = { 1 }, [1] = { 1 },
[2] = { 2 }, [2] = { 2 },
[3] = { 1, 2 }, [3] = { 1, 2 },
@ -10,116 +7,32 @@ local addonSets = {
[6] = { 2, 3 }, [6] = { 2, 3 },
[7] = { 1, 2, 3 } [7] = { 1, 2, 3 }
} }
local outfitWindow
local outfit
local outfits
local outfitCreature
local currentOutfit = 1
local addons
local currentColorBox
local currentClotheButtonBox
local colorBoxes = {}
local mount
local mounts
local mountCreature
local currentMount = 1
-- private functions
local function onAddonCheckChange(addon, value)
if addon:isChecked() then
outfit.addons = outfit.addons + value
else
outfit.addons = outfit.addons - value
end
outfitCreature:setOutfit(outfit)
end
local function onColorCheckChange(colorBox)
if colorBox == currentColorBox then
colorBox.onCheckChange = nil
colorBox:setChecked(true)
colorBox.onCheckChange = onColorCheckChange
else
currentColorBox.onCheckChange = nil
currentColorBox:setChecked(false)
currentColorBox.onCheckChange = onColorCheckChange
currentColorBox = colorBox
if currentClotheButtonBox:getId() == 'head' then outfitWindow = nil
outfit.head = currentColorBox.colorId outfit = nil
elseif currentClotheButtonBox:getId() == 'primary' then outfits = nil
outfit.body = currentColorBox.colorId outfitCreature = nil
elseif currentClotheButtonBox:getId() == 'secondary' then currentOutfit = 1
outfit.legs = currentColorBox.colorId
elseif currentClotheButtonBox:getId() == 'detail' then addons = nil
outfit.feet = currentColorBox.colorId currentColorBox = nil
end currentClotheButtonBox = nil
colorBoxes = {}
outfitCreature:setOutfit(outfit)
end mount = nil
end mounts = nil
mountCreature = nil
local function onClotheCheckChange(clotheButtonBox) currentMount = 1
if clotheButtonBox == currentClotheButtonBox then
clotheButtonBox.onCheckChange = nil function init()
clotheButtonBox:setChecked(true) connect(g_game, { onOpenOutfitWindow = create,
clotheButtonBox.onCheckChange = onClotheCheckChange onGameEnd = destroy })
else
currentClotheButtonBox.onCheckChange = nil
currentClotheButtonBox:setChecked(false)
currentClotheButtonBox.onCheckChange = onClotheCheckChange
currentClotheButtonBox = clotheButtonBox
local colorId = 0
if currentClotheButtonBox:getId() == 'head' then
colorId = outfit.head
elseif currentClotheButtonBox:getId() == 'primary' then
colorId = outfit.body
elseif currentClotheButtonBox:getId() == 'secondary' then
colorId = outfit.legs
elseif currentClotheButtonBox:getId() == 'detail' then
colorId = outfit.feet
end
outfitWindow:recursiveGetChildById('colorBox' .. colorId):setChecked(true)
end
end end
local function updateOutfit() function terminate()
if table.empty(outfits) or not outfit then disconnect(g_game, { onOpenOutfitWindow = create,
return onGameEnd = destroy })
end destroy()
local nameWidget = outfitWindow:getChildById('outfitName')
nameWidget:setText(outfits[currentOutfit][2])
local availableAddons = outfits[currentOutfit][3]
local prevAddons = {}
for k, addon in pairs(addons) do
prevAddons[k] = addon.widget:isChecked()
addon.widget:setChecked(false)
addon.widget:setEnabled(false)
end
if availableAddons > 0 then
for _, i in pairs(addonSets[availableAddons]) do
addons[i].widget:setEnabled(true)
end
end
outfit.addons = 0
for i = 1, #prevAddons do
local addon = prevAddons[i]
if addon and addons[i].widget:isEnabled() then
addons[i].widget:setChecked(true)
end
end
outfit.type = outfits[currentOutfit][1]
outfitCreature:setOutfit(outfit)
end end
function updateMount() function updateMount()
@ -128,30 +41,17 @@ function updateMount()
end end
local nameMountWidget = outfitWindow:getChildById('mountName') local nameMountWidget = outfitWindow:getChildById('mountName')
nameMountWidget:setText(mounts[currentMount][2]) nameMountWidget:setText(mounts[currentMount][2])
mount.type = mounts[currentMount][1] mount.type = mounts[currentMount][1]
mountCreature:setOutfit(mount) mountCreature:setOutfit(mount)
end end
-- public functions function create(creatureOutfit, outfitList, creatureMount, mountList)
function Outfit.init()
connect(g_game, { onOpenOutfitWindow = Outfit.create,
onGameEnd = Outfit.destroy })
end
function Outfit.terminate()
disconnect(g_game, { onOpenOutfitWindow = Outfit.create,
onGameEnd = Outfit.destroy })
Outfit.destroy()
Outfit = nil
end
function Outfit.create(creatureOutfit, outfitList, creatureMount, mountList)
outfitCreature = creatureOutfit outfitCreature = creatureOutfit
mountCreature = creatureMount mountCreature = creatureMount
outfits = outfitList outfits = outfitList
mounts = mountList mounts = mountList
Outfit.destroy() destroy()
outfitWindow = g_ui.displayUI('outfitwindow.otui') outfitWindow = g_ui.displayUI('outfitwindow.otui')
local colorBoxPanel = outfitWindow:getChildById('colorBoxPanel') local colorBoxPanel = outfitWindow:getChildById('colorBoxPanel')
@ -178,24 +78,24 @@ function Outfit.create(creatureOutfit, outfitList, creatureMount, mountList)
outfitWindow:getChildById('mountNextButton'):hide() outfitWindow:getChildById('mountNextButton'):hide()
outfitWindow:getChildById('mountPrevButton'):hide() outfitWindow:getChildById('mountPrevButton'):hide()
end end
-- set addons -- set addons
addons = { addons = {
[1] = {widget = outfitWindow:getChildById('addon1'), value = 1}, [1] = {widget = outfitWindow:getChildById('addon1'), value = 1},
[2] = {widget = outfitWindow:getChildById('addon2'), value = 2}, [2] = {widget = outfitWindow:getChildById('addon2'), value = 2},
[3] = {widget = outfitWindow:getChildById('addon3'), value = 4} [3] = {widget = outfitWindow:getChildById('addon3'), value = 4}
} }
for _, addon in pairs(addons) do for _, addon in pairs(addons) do
addon.widget.onCheckChange = function(self) onAddonCheckChange(self, addon.value) end addon.widget.onCheckChange = function(self) onAddonCheckChange(self, addon.value) end
end end
if outfit.addons > 0 then if outfit.addons > 0 then
for _, i in pairs(addonSets[outfit.addons]) do for _, i in pairs(ADDON_SETS[outfit.addons]) do
addons[i].widget:setChecked(true) addons[i].widget:setChecked(true)
end end
end end
-- hook outfit sections -- hook outfit sections
currentClotheButtonBox = outfitWindow:getChildById('head') currentClotheButtonBox = outfitWindow:getChildById('head')
outfitWindow:getChildById('head').onCheckChange = onClotheCheckChange outfitWindow:getChildById('head').onCheckChange = onClotheCheckChange
@ -241,7 +141,7 @@ function Outfit.create(creatureOutfit, outfitList, creatureMount, mountList)
updateMount() updateMount()
end end
function Outfit.destroy() function destroy()
if outfitWindow then if outfitWindow then
outfitWindow:destroy() outfitWindow:destroy()
outfitWindow = nil outfitWindow = nil
@ -253,14 +153,14 @@ function Outfit.destroy()
end end
end end
function Outfit.randomize() function randomize()
local outfitTemplate = { local outfitTemplate = {
outfitWindow:getChildById('head'), outfitWindow:getChildById('head'),
outfitWindow:getChildById('primary'), outfitWindow:getChildById('primary'),
outfitWindow:getChildById('secondary'), outfitWindow:getChildById('secondary'),
outfitWindow:getChildById('detail') outfitWindow:getChildById('detail')
} }
for i = 1, #outfitTemplate do for i = 1, #outfitTemplate do
outfitTemplate[i]:setChecked(true) outfitTemplate[i]:setChecked(true)
colorBoxes[math.random(1, #colorBoxes)]:setChecked(true) colorBoxes[math.random(1, #colorBoxes)]:setChecked(true)
@ -269,13 +169,13 @@ function Outfit.randomize()
outfitTemplate[1]:setChecked(true) outfitTemplate[1]:setChecked(true)
end end
function Outfit.accept() function accept()
if mount then outfit.mount = mount.type end if mount then outfit.mount = mount.type end
g_game.changeOutfit(outfit) g_game.changeOutfit(outfit)
Outfit.destroy() destroy()
end end
function Outfit.nextOutfitType() function nextOutfitType()
if not outfits then if not outfits then
return return
end end
@ -286,7 +186,7 @@ function Outfit.nextOutfitType()
updateOutfit() updateOutfit()
end end
function Outfit.previousOutfitType() function previousOutfitType()
if not outfits then if not outfits then
return return
end end
@ -297,7 +197,7 @@ function Outfit.previousOutfitType()
updateOutfit() updateOutfit()
end end
function Outfit.nextMountType() function nextMountType()
if not mounts then if not mounts then
return return
end end
@ -308,7 +208,7 @@ function Outfit.nextMountType()
updateMount() updateMount()
end end
function Outfit.previousMountType() function previousMountType()
if not mounts then if not mounts then
return return
end end
@ -318,3 +218,99 @@ function Outfit.previousMountType()
end end
updateMount() updateMount()
end end
function onAddonCheckChange(addon, value)
if addon:isChecked() then
outfit.addons = outfit.addons + value
else
outfit.addons = outfit.addons - value
end
outfitCreature:setOutfit(outfit)
end
function onColorCheckChange(colorBox)
if colorBox == currentColorBox then
colorBox.onCheckChange = nil
colorBox:setChecked(true)
colorBox.onCheckChange = onColorCheckChange
else
currentColorBox.onCheckChange = nil
currentColorBox:setChecked(false)
currentColorBox.onCheckChange = onColorCheckChange
currentColorBox = colorBox
if currentClotheButtonBox:getId() == 'head' then
outfit.head = currentColorBox.colorId
elseif currentClotheButtonBox:getId() == 'primary' then
outfit.body = currentColorBox.colorId
elseif currentClotheButtonBox:getId() == 'secondary' then
outfit.legs = currentColorBox.colorId
elseif currentClotheButtonBox:getId() == 'detail' then
outfit.feet = currentColorBox.colorId
end
outfitCreature:setOutfit(outfit)
end
end
function onClotheCheckChange(clotheButtonBox)
if clotheButtonBox == currentClotheButtonBox then
clotheButtonBox.onCheckChange = nil
clotheButtonBox:setChecked(true)
clotheButtonBox.onCheckChange = onClotheCheckChange
else
currentClotheButtonBox.onCheckChange = nil
currentClotheButtonBox:setChecked(false)
currentClotheButtonBox.onCheckChange = onClotheCheckChange
currentClotheButtonBox = clotheButtonBox
local colorId = 0
if currentClotheButtonBox:getId() == 'head' then
colorId = outfit.head
elseif currentClotheButtonBox:getId() == 'primary' then
colorId = outfit.body
elseif currentClotheButtonBox:getId() == 'secondary' then
colorId = outfit.legs
elseif currentClotheButtonBox:getId() == 'detail' then
colorId = outfit.feet
end
outfitWindow:recursiveGetChildById('colorBox' .. colorId):setChecked(true)
end
end
function updateOutfit()
if table.empty(outfits) or not outfit then
return
end
local nameWidget = outfitWindow:getChildById('outfitName')
nameWidget:setText(outfits[currentOutfit][2])
local availableAddons = outfits[currentOutfit][3]
local prevAddons = {}
for k, addon in pairs(addons) do
prevAddons[k] = addon.widget:isChecked()
addon.widget:setChecked(false)
addon.widget:setEnabled(false)
end
if availableAddons > 0 then
for _, i in pairs(ADDON_SETS[availableAddons]) do
addons[i].widget:setEnabled(true)
end
end
outfit.addons = 0
for i = 1, #prevAddons do
local addon = prevAddons[i]
if addon and addons[i].widget:isEnabled() then
addons[i].widget:setChecked(true)
end
end
outfit.type = outfits[currentOutfit][1]
outfitCreature:setOutfit(outfit)
end

@ -3,13 +3,7 @@ Module
description: Change local player outfit description: Change local player outfit
author: baxnie, edubart author: baxnie, edubart
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ outfit.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'outfit'
Outfit.init()
@onUnload: |
Outfit.terminate()

@ -31,8 +31,8 @@ Window
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
anchors.verticalCenter: parent.verticalCenter anchors.verticalCenter: parent.verticalCenter
@onEnter: Outfit.accept() @onEnter: accept()
@onEscape: Outfit.destroy() @onEscape: destroy()
// Creature Boxes // Creature Boxes
@ -59,7 +59,7 @@ Window
anchors.verticalCenter: outfitCreatureBox.verticalCenter anchors.verticalCenter: outfitCreatureBox.verticalCenter
margin-left: 3 margin-left: 3
enabled: true enabled: true
@onClick: Outfit.nextOutfitType() @onClick: nextOutfitType()
PrevOutfitButton PrevOutfitButton
id: outfitPrevButton id: outfitPrevButton
@ -67,7 +67,7 @@ Window
anchors.verticalCenter: outfitCreatureBox.verticalCenter anchors.verticalCenter: outfitCreatureBox.verticalCenter
margin-right: 3 margin-right: 3
enabled: true enabled: true
@onClick: Outfit.previousOutfitType() @onClick: previousOutfitType()
Creature Creature
id: mountCreatureBox id: mountCreatureBox
@ -92,7 +92,7 @@ Window
anchors.verticalCenter: mountCreatureBox.verticalCenter anchors.verticalCenter: mountCreatureBox.verticalCenter
margin-left: 3 margin-left: 3
enabled: true enabled: true
@onClick: Outfit.nextMountType() @onClick: nextMountType()
PrevMountButton PrevMountButton
id: mountPrevButton id: mountPrevButton
@ -100,7 +100,7 @@ Window
anchors.verticalCenter: mountCreatureBox.verticalCenter anchors.verticalCenter: mountCreatureBox.verticalCenter
margin-right: 3 margin-right: 3
enabled: true enabled: true
@onClick: Outfit.previousMountType() @onClick: previousMountType()
// Addon Check Boxes // Addon Check Boxes
@ -189,7 +189,7 @@ Window
anchors.left: prev.left anchors.left: prev.left
anchors.top: prev.bottom anchors.top: prev.bottom
margin-right: 16 margin-right: 16
@onClick: Outfit.randomize() @onClick: randomize()
HorizontalSeparator HorizontalSeparator
anchors.left: parent.left anchors.left: parent.left
@ -208,7 +208,7 @@ Window
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
margin-bottom: 16 margin-bottom: 16
margin-right: 16 margin-right: 16
@onClick: Outfit.accept() @onClick: accept()
Button Button
id: outfitCancelButton id: outfitCancelButton
@ -218,4 +218,4 @@ Window
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
margin-bottom: 16 margin-bottom: 16
margin-right: 16 margin-right: 16
@onClick: Outfit.destroy() @onClick: destroy()

@ -1,51 +1,42 @@
PlayerDeath = {} deathWindow = nil
-- private variables function init()
local deathWindow
-- private functions
-- public functions
function PlayerDeath.init()
g_ui.importStyle('deathwindow.otui') g_ui.importStyle('deathwindow.otui')
connect(g_game, { onDeath = PlayerDeath.display, connect(g_game, { onDeath = display,
onGameEnd = PlayerDeath.reset }) onGameEnd = reset })
end end
function PlayerDeath.terminate() function terminate()
disconnect(g_game, { onDeath = PlayerDeath.display, disconnect(g_game, { onDeath = display,
onGameEnd = PlayerDeath.reset }) onGameEnd = reset })
PlayerDeath.reset() reset()
PlayerDeath = nil
end end
function PlayerDeath.reset() function reset()
if deathWindow then if deathWindow then
deathWindow:destroy() deathWindow:destroy()
deathWindow = nil deathWindow = nil
end end
end end
function PlayerDeath.display() function display()
PlayerDeath.displayDeadMessage() displayDeadMessage()
PlayerDeath.openWindow() openWindow()
end end
function PlayerDeath.displayDeadMessage() function displayDeadMessage()
local advanceLabel = GameInterface.getMapPanel():recursiveGetChildById('centerAdvance') local advanceLabel = modules.game_interface.getMapPanel():recursiveGetChildById('centerAdvance')
if advanceLabel:isVisible() then if advanceLabel:isVisible() then
return return
end end
TextMessage.displayEventAdvance(tr('You are dead.')) modules.game_textmessage.displayEventAdvance(tr('You are dead.'))
end end
function PlayerDeath.openWindow() function openWindow()
if deathWindow then if deathWindow then return end
return
end
deathWindow = g_ui.createWidget('DeathWindow', rootWidget) deathWindow = g_ui.createWidget('DeathWindow', rootWidget)
local okButton = deathWindow:getChildById('buttonOk') local okButton = deathWindow:getChildById('buttonOk')
local cancelButton = deathWindow:getChildById('buttonCancel') local cancelButton = deathWindow:getChildById('buttonCancel')
@ -56,7 +47,7 @@ function PlayerDeath.openWindow()
deathWindow = nil deathWindow = nil
end end
local cancelFunc = function() local cancelFunc = function()
GameInterface.logout() modules.game_interface.logout()
cancelButton:getParent():destroy() cancelButton:getParent():destroy()
deathWindow = nil deathWindow = nil
end end
@ -66,4 +57,4 @@ function PlayerDeath.openWindow()
okButton.onClick = okFunc okButton.onClick = okFunc
cancelButton.onClick = cancelFunc cancelButton.onClick = cancelFunc
end end

@ -3,15 +3,7 @@ Module
description: Manage player deaths description: Manage player deaths
author: BeniS, edubart author: BeniS, edubart
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ playerdeath.lua ]
- game_interface @onLoad: init()
- game_textmessage @onUnload: terminate()
- client_entergame
@onLoad: |
dofile 'playerdeath'
PlayerDeath.init()
@onUnload: |
PlayerDeath.terminate()

@ -1,23 +1,19 @@
PlayerMount = {} function init()
function PlayerMount.init()
if g_game.getFeature(GamePlayerMount) then if g_game.getFeature(GamePlayerMount) then
g_keyboard.bindKeyDown('Ctrl+R', PlayerMount.toggleMount, gameRootPanel) g_keyboard.bindKeyDown('Ctrl+R', toggleMount, gameRootPanel)
end end
end end
function PlayerMount.terminate() function terminate()
if g_game.getFeature(GamePlayerMount) then if g_game.getFeature(GamePlayerMount) then
g_keyboard.unbindKeyDown('Ctrl+R', gameRootPanel) g_keyboard.unbindKeyDown('Ctrl+R', gameRootPanel)
end end
PlayerMount = nil
end end
function PlayerMount.toggleMount() function toggleMount()
g_game.mount(not g_game.isMounted()) g_game.mount(not g_game.isMounted())
end end
function PlayerMount.dismount() function dismount()
g_game.mount(false) g_game.mount(false)
end end

@ -3,10 +3,7 @@ Module
description: Manage player mounts description: Manage player mounts
author: BeniS author: BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
@onLoad: | scripts: [playermount.lua]
dofile 'playermount' @onLoad: init()
PlayerMount.init() @onUnload: terminate()
@onUnload: |
PlayerMount.terminate()

@ -1,16 +1,34 @@
PlayerTrade = {} tradeWindow = nil
local tradeWindow function init()
g_ui.importStyle('tradewindow.otui')
connect(g_game, { onOwnTrade = onGameOwnTrade,
onCounterTrade = onGameCounterTrade,
onCloseTrade = onGameCloseTrade,
onGameEnd = onGameCloseTrade })
end
function terminate()
disconnect(g_game, { onOwnTrade = onGameOwnTrade,
onCounterTrade = onGameCounterTrade,
onCloseTrade = onGameCloseTrade,
onGameEnd = onGameCloseTrade })
local function createTrade() if tradeWindow then
tradeWindow = g_ui.createWidget('TradeWindow', GameInterface.getRightPanel()) tradeWindow:destroy()
end
end
function createTrade()
tradeWindow = g_ui.createWidget('TradeWindow', modules.game_interface.getRightPanel())
tradeWindow.onClose = function() tradeWindow.onClose = function()
g_game.rejectTrade() g_game.rejectTrade()
tradeWindow:hide() tradeWindow:hide()
end end
end end
local function fillTrade(name, items, counter) function fillTrade(name, items, counter)
if not tradeWindow then if not tradeWindow then
createTrade() createTrade()
end end
@ -42,37 +60,16 @@ local function fillTrade(name, items, counter)
end end
end end
local function onGameOwnTrade(name, items) function onGameOwnTrade(name, items)
fillTrade(name, items, false) fillTrade(name, items, false)
end end
local function onGameCounterTrade(name, items) function onGameCounterTrade(name, items)
fillTrade(name, items, true) fillTrade(name, items, true)
end end
local function onGameCloseTrade() function onGameCloseTrade()
if not tradeWindow then return end if not tradeWindow then return end
tradeWindow:destroy() tradeWindow:destroy()
tradeWindow = nil tradeWindow = nil
end end
function PlayerTrade.init()
g_ui.importStyle('tradewindow.otui')
connect(g_game, { onOwnTrade = onGameOwnTrade,
onCounterTrade = onGameCounterTrade,
onCloseTrade = onGameCloseTrade,
onGameEnd = onGameCloseTrade })
end
function PlayerTrade.terminate()
disconnect(g_game, { onOwnTrade = onGameOwnTrade,
onCounterTrade = onGameCounterTrade,
onCloseTrade = onGameCloseTrade,
onGameEnd = onGameCloseTrade })
if tradeWindow then
tradeWindow:destroy()
tradeWindow = nil
end
end

@ -3,13 +3,7 @@ Module
description: Allow to trade items with players description: Allow to trade items with players
author: edubart author: edubart
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ playertrade.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'playertrade'
PlayerTrade.init()
@onUnload: |
PlayerTrade.terminate()

@ -1,11 +1,39 @@
QuestLog = {} questLogButton = nil
questLineWindow = nil
local questLogButton function init()
local questLogWindow g_ui.importStyle('questlogwindow.otui')
local questLineWindow g_ui.importStyle('questlinewindow.otui')
questLogButton = TopMenu.addLeftGameButton('questLogButton', tr('Quest Log'), 'questlog.png', function() g_game.requestQuestLog() end)
local function onGameQuestLog(quests) connect(g_game, { onQuestLog = onGameQuestLog,
QuestLog.destroyWindows() onQuestLine = onGameQuestLine,
onGameEnd = destroyWindows})
end
function terminate()
disconnect(g_game, { onQuestLog = onGameQuestLog,
onQuestLine = onGameQuestLine,
onGameEnd = destroyWindows})
destroyWindows()
end
function destroyWindows()
if questLogWindow then
questLogWindow:destroy()
questLogWindow = nil
end
if questLineWindow then
questLineWindow:destroy()
questLineWindow = nil
end
end
function onGameQuestLog(quests)
destroyWindows()
questLogWindow = g_ui.createWidget('QuestLogWindow', rootWidget) questLogWindow = g_ui.createWidget('QuestLogWindow', rootWidget)
local questList = questLogWindow:getChildById('questList') local questList = questLogWindow:getChildById('questList')
@ -27,7 +55,7 @@ local function onGameQuestLog(quests)
end end
end end
local function onGameQuestLine(questId, questMissions) function onGameQuestLine(questId, questMissions)
if questLogWindow then questLogWindow:hide() end if questLogWindow then questLogWindow:hide() end
if questLineWindow then questLineWindow:destroy() end if questLineWindow then questLineWindow:destroy() end
@ -53,37 +81,3 @@ local function onGameQuestLine(questId, questMissions)
questLineWindow = nil questLineWindow = nil
end end
end end
function QuestLog.init()
g_ui.importStyle('questlogwindow.otui')
g_ui.importStyle('questlinewindow.otui')
questLogButton = TopMenu.addLeftGameButton('questLogButton', tr('Quest Log'), 'questlog.png', function() g_game.requestQuestLog() end)
connect(g_game, { onQuestLog = onGameQuestLog,
onQuestLine = onGameQuestLine,
onGameEnd = QuestLog.destroyWindows})
end
function QuestLog.destroyWindows()
if questLogWindow then
questLogWindow:destroy()
questLogWindow = nil
end
if questLineWindow then
questLineWindow:destroy()
questLineWindow = nil
end
end
function QuestLog.terminate()
disconnect(g_game, { onQuestLog = onGameQuestLog,
onQuestLine = onGameQuestLine,
onGameEnd = QuestLog.destroyWindows})
QuestLog.destroyWindows()
questLogButton:destroy()
questLogButton = nil
end

@ -3,13 +3,7 @@ Module
description: View game quests status description: View game quests status
author: edubart author: edubart
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ questlog.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'questlog'
QuestLog.init()
@onUnload: |
QuestLog.terminate()

@ -1,7 +1,4 @@
RuleViolation = {} rvreasons = {}
-- private variables
local rvreasons = {}
rvreasons[1] = tr("1a) Offensive Name") rvreasons[1] = tr("1a) Offensive Name")
rvreasons[2] = tr("1b) Invalid Name Format") rvreasons[2] = tr("1b) Invalid Name Format")
rvreasons[3] = tr("1c) Unsuitable Name") rvreasons[3] = tr("1c) Unsuitable Name")
@ -24,7 +21,7 @@ rvreasons[19] = tr("4c) False Report to Gamemaster")
rvreasons[20] = tr("Destructive Behaviour") rvreasons[20] = tr("Destructive Behaviour")
rvreasons[21] = tr("Excessive Unjustified Player Killing") rvreasons[21] = tr("Excessive Unjustified Player Killing")
local rvactions = {} rvactions = {}
rvactions[0] = tr("Notation") rvactions[0] = tr("Notation")
rvactions[1] = tr("Name Report") rvactions[1] = tr("Name Report")
rvactions[2] = tr("Banishment") rvactions[2] = tr("Banishment")
@ -33,31 +30,12 @@ rvactions[4] = tr("Banishment + Final Warning")
rvactions[5] = tr("Name Report + Banishment + Final Warning") rvactions[5] = tr("Name Report + Banishment + Final Warning")
rvactions[6] = tr("Statement Report") rvactions[6] = tr("Statement Report")
local ruleViolationWindow ruleViolationWindow = nil
local reasonsTextList reasonsTextList = nil
local actionsTextList actionsTextList = nil
-- public functions
function RuleViolation.hasWindowAccess()
return reasonsTextList:getChildCount() > 0
end
function RuleViolation.loadReasons()
reasonsTextList:destroyChildren()
local actions = g_game.getGMActions()
for reason, actionFlags in pairs(actions) do
local label = g_ui.createWidget('RVListLabel', reasonsTextList)
label:setText(rvreasons[reason])
label.reasonId = reason
label.actionFlags = actionFlags
end
if not RuleViolation.hasWindowAccess() and ruleViolationWindow:isVisible() then RuleViolation.hide() end
end
function RuleViolation.init() function init()
connect(g_game, { onGMActions = RuleViolation.loadReasons }) connect(g_game, { onGMActions = loadReasons })
ruleViolationWindow = g_ui.displayUI('ruleviolation.otui') ruleViolationWindow = g_ui.displayUI('ruleviolation.otui')
ruleViolationWindow:setVisible(false) ruleViolationWindow:setVisible(false)
@ -65,25 +43,40 @@ function RuleViolation.init()
reasonsTextList = ruleViolationWindow:getChildById('reasonList') reasonsTextList = ruleViolationWindow:getChildById('reasonList')
actionsTextList = ruleViolationWindow:getChildById('actionList') actionsTextList = ruleViolationWindow:getChildById('actionList')
g_keyboard.bindKeyDown('Ctrl+Y', RuleViolation.show) g_keyboard.bindKeyDown('Ctrl+Y', show)
if g_game.isOnline() then if g_game.isOnline() then
RuleViolation.loadReasons() loadReasons()
end end
end end
function RuleViolation.terminate() function terminate()
disconnect(g_game, { onGMActions = RuleViolation.loadReasons }) disconnect(g_game, { onGMActions = loadReasons })
g_keyboard.unbindKeyDown('Ctrl+Y')
ruleViolationWindow:destroy() ruleViolationWindow:destroy()
ruleViolationWindow = nil end
reasonsTextList = nil function hasWindowAccess()
actionsTextList = nil return reasonsTextList:getChildCount() > 0
end end
function RuleViolation.show(target, statement) function loadReasons()
if g_game.isOnline() and RuleViolation.hasWindowAccess() then reasonsTextList:destroyChildren()
local actions = g_game.getGMActions()
for reason, actionFlags in pairs(actions) do
local label = g_ui.createWidget('RVListLabel', reasonsTextList)
label:setText(rvreasons[reason])
label.reasonId = reason
label.actionFlags = actionFlags
end
if not hasWindowAccess() and ruleViolationWindow:isVisible() then hide() end
end
function show(target, statement)
if g_game.isOnline() and hasWindowAccess() then
if target then if target then
ruleViolationWindow:getChildById('nameText'):setText(target) ruleViolationWindow:getChildById('nameText'):setText(target)
end end
@ -97,12 +90,12 @@ function RuleViolation.show(target, statement)
end end
end end
function RuleViolation.hide() function hide()
ruleViolationWindow:hide() ruleViolationWindow:hide()
RuleViolation.clearForm() clearForm()
end end
function RuleViolation.onSelectReason(reasonLabel, focused) function onSelectReason(reasonLabel, focused)
if reasonLabel.actionFlags and focused then if reasonLabel.actionFlags and focused then
actionsTextList:destroyChildren() actionsTextList:destroyChildren()
for actionBaseFlag = 0, #rvactions do for actionBaseFlag = 0, #rvactions do
@ -116,7 +109,7 @@ function RuleViolation.onSelectReason(reasonLabel, focused)
end end
end end
function RuleViolation.report() function report()
local target = ruleViolationWindow:getChildById('nameText'):getText() local target = ruleViolationWindow:getChildById('nameText'):getText()
local reason = reasonsTextList:getFocusedChild().reasonId local reason = reasonsTextList:getFocusedChild().reasonId
local action = actionsTextList:getFocusedChild().actionId local action = actionsTextList:getFocusedChild().actionId
@ -130,13 +123,13 @@ function RuleViolation.report()
displayErrorBox(tr("Error"), tr("You must enter a comment.")) displayErrorBox(tr("Error"), tr("You must enter a comment."))
else else
g_game.reportRuleVilation(target, reason, action, comment, statement, statementId, ipBanishment) g_game.reportRuleVilation(target, reason, action, comment, statement, statementId, ipBanishment)
RuleViolation.hide() hide()
end end
end end
function RuleViolation.clearForm() function clearForm()
ruleViolationWindow:getChildById('nameText'):clearText() ruleViolationWindow:getChildById('nameText'):clearText()
ruleViolationWindow:getChildById('commentText'):clearText() ruleViolationWindow:getChildById('commentText'):clearText()
ruleViolationWindow:getChildById('statementText'):clearText() ruleViolationWindow:getChildById('statementText'):clearText()
ruleViolationWindow:getChildById('ipBanCheckBox'):setChecked(false) ruleViolationWindow:getChildById('ipBanCheckBox'):setChecked(false)
end end

@ -3,13 +3,7 @@ Module
description: Rule violation interface (Ctrl+Y) description: Rule violation interface (Ctrl+Y)
author: andrefaramir author: andrefaramir
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: scripts: [ ruleviolation.lua ]
- game_interface @onLoad: init()
@onUnload: terminate()
@onLoad: |
dofile 'ruleviolation'
RuleViolation.init()
@onUnload: |
RuleViolation.terminate()

@ -3,7 +3,7 @@ RVListLabel < Label
text-offset: 2 0 text-offset: 2 0
focusable: true focusable: true
@onFocusChange: function (self, focused) RuleViolation.onSelectReason(self, focused) end @onFocusChange: function (self, focused) RuleViolation.onSelectReason(self, focused) end
$focus: $focus:
background-color: #ffffff22 background-color: #ffffff22
color: #ffffff color: #ffffff
@ -11,10 +11,10 @@ RVListLabel < Label
RVLabel < Label RVLabel < Label
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right
$first: $first:
anchors.top: parent.top anchors.top: parent.top
$!first: $!first:
margin-top: 10 margin-top: 10
anchors.top: prev.bottom anchors.top: prev.bottom
@ -23,34 +23,34 @@ RVTextEdit < TextEdit
margin-top: 2 margin-top: 2
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right
$first: $first:
anchors.top: parent.top anchors.top: parent.top
$!first: $!first:
anchors.top: prev.bottom anchors.top: prev.bottom
MainWindow MainWindow
id: ruleViolationWindow id: ruleViolationWindow
size: 400 445 size: 400 445
text: Rule Violation text: Rule Violation
RVLabel RVLabel
!text: tr('Name:') !text: tr('Name:')
RVTextEdit RVTextEdit
id: nameText id: nameText
RVLabel RVLabel
!text: tr('Statement:') !text: tr('Statement:')
RVTextEdit RVTextEdit
id: statementText id: statementText
enabled: false enabled: false
RVLabel RVLabel
!text: tr('Reason:') !text: tr('Reason:')
TextList TextList
id: reasonList id: reasonList
height: 100 height: 100
@ -67,11 +67,11 @@ MainWindow
anchors.bottom: reasonList.bottom anchors.bottom: reasonList.bottom
anchors.right: reasonList.right anchors.right: reasonList.right
step: 14 step: 14
pixels-scroll: true pixels-scroll: true
RVLabel RVLabel
!text: tr('Action:') !text: tr('Action:')
TextList TextList
id: actionList id: actionList
height: 60 height: 60
@ -88,8 +88,8 @@ MainWindow
anchors.bottom: actionList.bottom anchors.bottom: actionList.bottom
anchors.right: actionList.right anchors.right: actionList.right
step: 14 step: 14
pixels-scroll: true pixels-scroll: true
CheckBox CheckBox
id: ipBanCheckBox id: ipBanCheckBox
!text: tr('IP Address Banishment') !text: tr('IP Address Banishment')
@ -97,24 +97,24 @@ MainWindow
anchors.top: prev.bottom anchors.top: prev.bottom
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right
RVLabel RVLabel
!text: tr('Comment:') !text: tr('Comment:')
RVTextEdit RVTextEdit
id: commentText id: commentText
Button Button
!text: tr('Cancel') !text: tr('Cancel')
width: 64 width: 64
anchors.right: parent.right anchors.right: parent.right
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
@onClick: RuleViolation.hide() @onClick: RuleViolation.hide()
Button Button
!text: tr('Ok') !text: tr('Ok')
width: 64 width: 64
margin-right: 5 margin-right: 5
anchors.right: prev.left anchors.right: prev.left
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
@onClick: RuleViolation.report() @onClick: RuleViolation.report()

@ -1,7 +1,5 @@
Shaders = {} HOTKEY = 'Ctrl+X'
MAP_SHADERS = {
local HOTKEY = 'Ctrl+X'
local MAP_SHADERS = {
{ name = 'Default', frag = 'shaders/default.frag' }, { name = 'Default', frag = 'shaders/default.frag' },
{ name = 'Bloom', frag = 'shaders/bloom.frag'}, { name = 'Bloom', frag = 'shaders/bloom.frag'},
{ name = 'Sepia', frag ='shaders/sepia.frag' }, { name = 'Sepia', frag ='shaders/sepia.frag' },
@ -16,23 +14,23 @@ local MAP_SHADERS = {
{ name = 'Noise', frag ='shaders/noise.frag' }, { name = 'Noise', frag ='shaders/noise.frag' },
} }
local ITEM_SHADERS = { ITEM_SHADERS = {
{ name = 'Fake 3D', vert = 'shaders/fake3d.vert' } { name = 'Fake 3D', vert = 'shaders/fake3d.vert' }
} }
local shadersPanel shadersPanel = nil
function Shaders.init() function init()
g_ui.importStyle('shaders.otui') g_ui.importStyle('shaders.otui')
g_keyboard.bindKeyDown(HOTKEY, Shaders.toggle) g_keyboard.bindKeyDown(HOTKEY, toggle)
shadersPanel = g_ui.createWidget('ShadersPanel', GameInterface.getMapPanel()) shadersPanel = g_ui.createWidget('ShadersPanel', modules.game_interface.getMapPanel())
shadersPanel:hide() shadersPanel:hide()
local mapComboBox = shadersPanel:getChildById('mapComboBox') local mapComboBox = shadersPanel:getChildById('mapComboBox')
mapComboBox.onOptionChange = function(combobox, option) mapComboBox.onOptionChange = function(combobox, option)
local map = GameInterface.getMapPanel() local map = modules.game_interface.getMapPanel()
map:setMapShader(g_shaders.getShader(option)) map:setMapShader(g_shaders.getShader(option))
end end
@ -51,16 +49,15 @@ function Shaders.init()
mapComboBox:addOption(opts.name) mapComboBox:addOption(opts.name)
end end
local map = GameInterface.getMapPanel() local map = modules.game_interface.getMapPanel()
map:setMapShader(g_shaders.getShader('Default')) map:setMapShader(g_shaders.getShader('Default'))
end end
function Shaders.terminate() function terminate()
g_keyboard.unbindKeyDown(HOTKEY) g_keyboard.unbindKeyDown(HOTKEY)
shadersPanel:destroy() shadersPanel:destroy()
shadersPanel = nil
end end
function Shaders.toggle() function toggle()
shadersPanel:setVisible(not shadersPanel:isVisible()) shadersPanel:setVisible(not shadersPanel:isVisible())
end end

@ -3,13 +3,6 @@ Module
description: Manage game shaders description: Manage game shaders
author: edubart author: edubart
website: www.otclient.info website: www.otclient.info
scripts: [ shaders.lua ]
dependencies: @onLoad: init()
- game_interface @onUnload: terminate()
@onLoad: |
dofile 'shaders'
Shaders.init()
@onUnload: |
Shaders.terminate()

@ -14,7 +14,7 @@ function init()
onSkillChange = onSkillChange onSkillChange = onSkillChange
}) })
skillsWindow = g_ui.loadUI('skills.otui', GameInterface.getRightPanel()) skillsWindow = g_ui.loadUI('skills.otui', modules.game_interface.getRightPanel())
skillsButton = TopMenu.addRightGameToggleButton('skillsButton', tr('Skills') .. ' (Ctrl+S)', 'skills.png', toggle) skillsButton = TopMenu.addRightGameToggleButton('skillsButton', tr('Skills') .. ' (Ctrl+S)', 'skills.png', toggle)
skillsButton:setOn(true) skillsButton:setOn(true)
g_keyboard.bindKeyDown('Ctrl+S', toggle) g_keyboard.bindKeyDown('Ctrl+S', toggle)

@ -26,7 +26,7 @@ function init()
registerProtocol() registerProtocol()
g_ui.importStyle('textmessage.otui') g_ui.importStyle('textmessage.otui')
centerTextMessagePanel = g_ui.createWidget('Panel', GameInterface.getMapPanel()) centerTextMessagePanel = g_ui.createWidget('Panel', modules.game_interface.getMapPanel())
centerTextMessagePanel:setId('centerTextMessagePanel') centerTextMessagePanel:setId('centerTextMessagePanel')
local layout = UIVerticalLayout.create(centerTextMessagePanel) local layout = UIVerticalLayout.create(centerTextMessagePanel)
@ -38,15 +38,8 @@ function init()
warningLabel = createTextMessageLabel('warningLabel', centerTextMessagePanel, 'CenterLabel') warningLabel = createTextMessageLabel('warningLabel', centerTextMessagePanel, 'CenterLabel')
advanceLabel = createTextMessageLabel('advanceLabel', centerTextMessagePanel, 'CenterLabel') advanceLabel = createTextMessageLabel('advanceLabel', centerTextMessagePanel, 'CenterLabel')
infoLabel = createTextMessageLabel('infoLabel', centerTextMessagePanel, 'CenterLabel') infoLabel = createTextMessageLabel('infoLabel', centerTextMessagePanel, 'CenterLabel')
privateLabel = createTextMessageLabel('privateLabel', GameInterface.getMapPanel(), 'TopCenterLabel') privateLabel = createTextMessageLabel('privateLabel', modules.game_interface.getMapPanel(), 'TopCenterLabel')
statusLabel = createTextMessageLabel('statusLabel', GameInterface.getMapPanel(), 'BottomLabel') statusLabel = createTextMessageLabel('statusLabel', modules.game_interface.getMapPanel(), 'BottomLabel')
export({
clearMessages = clearMessages,
displayStatus = function(msg, time) displayMessage('StatusSmall', msg) end,
displayEventAdvance = function(msg, time) displayMessage('EventAdvance', msg, time) end,
displayPrivate = function(msg, time) displayMessage('Private', time) end
}, 'TextMessage')
end end
function terminate() function terminate()
@ -65,8 +58,6 @@ function terminate()
centerTextMessagePanel:destroy() centerTextMessagePanel:destroy()
statusLabel:destroy() statusLabel:destroy()
privateLabel:destroy() privateLabel:destroy()
unexport('TextMessage')
end end
function clearMessages() function clearMessages()
@ -90,12 +81,12 @@ function displayMessage(msgtype, msg, time)
if msgtype.consoleTab ~= nil then if msgtype.consoleTab ~= nil then
if msgtype.consoleOption == nil or Options.getOption(msgtype.consoleOption) then if msgtype.consoleOption == nil or Options.getOption(msgtype.consoleOption) then
Console.addText(msg, msgtype, msgtype.consoleTab) modules.game_console.addText(msg, msgtype, msgtype.consoleTab)
end end
end end
if msgtype.labelId then if msgtype.labelId then
local label = GameInterface.getMapPanel():recursiveGetChildById(msgtype.labelId) local label = modules.game_interface.getMapPanel():recursiveGetChildById(msgtype.labelId)
label:setText(msg) label:setText(msg)
label:setColor(msgtype.color) label:setColor(msgtype.color)
@ -110,3 +101,15 @@ function displayMessage(msgtype, msg, time)
label.hideEvent = scheduleEvent(function() label:setVisible(false) end, time) label.hideEvent = scheduleEvent(function() label:setVisible(false) end, time)
end end
end end
function displayStatus(msg, time)
displayMessage('StatusSmall', msg)
end
function displayEventAdvance(msg, time)
displayMessage('EventAdvance', msg, time)
end
function displayPrivate(msg, time)
displayMessage('Private', time)
end

@ -1,13 +1,28 @@
TextWindow = {} function init()
g_ui.importStyle('textwindow.otui')
connect(g_game, { onEditText = onGameEditText,
onEditList = onGameEditList,
onGameEnd = destroy })
end
function terminate()
disconnect(g_game, { onEditText = onGameEditText,
onEditList = onGameEditList,
onGameEnd = destroy })
-- private variables destroy()
local textWindow end
-- private functions function destroy()
local function onGameEditText(id, itemId, maxLength, text, writter, time)
if textWindow then if textWindow then
return textWindow:destroy()
textWindow = nil
end end
end
function onGameEditText(id, itemId, maxLength, text, writter, time)
if textWindow then return end
textWindow = g_ui.createWidget('TextWindow', rootWidget) textWindow = g_ui.createWidget('TextWindow', rootWidget)
local writeable = (maxLength ~= #text) and maxLength > 0 local writeable = (maxLength ~= #text) and maxLength > 0
@ -52,18 +67,16 @@ local function onGameEditText(id, itemId, maxLength, text, writter, time)
if writeable then if writeable then
g_game.editText(id, textEdit:getText()) g_game.editText(id, textEdit:getText())
end end
TextWindow.destroy() destroy()
end end
okButton.onClick = doneFunc okButton.onClick = doneFunc
textWindow.onEnter = doneFunc textWindow.onEnter = doneFunc
textWindow.onEscape = TextWindow.destroy textWindow.onEscape = destroy
end end
local function onGameEditList(id, doorId, text) function onGameEditList(id, doorId, text)
if textWindow then if textWindow then return end
return
end
textWindow = g_ui.createWidget('TextWindow', rootWidget) textWindow = g_ui.createWidget('TextWindow', rootWidget)
local textEdit = textWindow:getChildById('text') local textEdit = textWindow:getChildById('text')
@ -79,34 +92,10 @@ local function onGameEditList(id, doorId, text)
doneFunc = function() doneFunc = function()
g_game.editList(id, doorId, textEdit:getText()) g_game.editList(id, doorId, textEdit:getText())
TextWindow.destroy() destroy()
end end
okButton.onClick = doneFunc okButton.onClick = doneFunc
textWindow.onEnter = doneFunc textWindow.onEnter = doneFunc
textWindow.onEscape = TextWindow.destroy textWindow.onEscape = destroy
end
-- public functions
function TextWindow.init()
g_ui.importStyle('textwindow.otui')
connect(g_game, { onEditText = onGameEditText,
onEditList = onGameEditList,
onGameEnd = TextWindow.destroy })
end
function TextWindow.terminate()
disconnect(g_game, { onEditText = onGameEditText,
onEditList = onGameEditList,
onGameEnd = TextWindow.destroy })
TextWindow.destroy()
end end
function TextWindow.destroy()
if textWindow then
textWindow:destroy()
textWindow = nil
end
end

@ -3,13 +3,8 @@ Module
description: Allow to edit text books and lists description: Allow to edit text books and lists
author: edubart, BeniS author: edubart, BeniS
website: www.otclient.info website: www.otclient.info
sandboxed: true
dependencies: dependencies: [ game_interface ]
- game_interface scripts: [ textwindow.lua ]
@onLoad: init()
@onLoad: | @onUnload: terminate()
dofile 'textwindow'
TextWindow.init()
@onUnload: |
TextWindow.terminate()

@ -1,6 +1,4 @@
TibiaFiles = {} function init()
function TibiaFiles.init()
if not g_things.loadDat('/game_tibiafiles/Tibia.dat') then if not g_things.loadDat('/game_tibiafiles/Tibia.dat') then
fatal(tr("Unable to load dat file, please place a valid Tibia dat in modules/game_tibiafiles/Tibia.dat")) fatal(tr("Unable to load dat file, please place a valid Tibia dat in modules/game_tibiafiles/Tibia.dat"))
end end
@ -9,5 +7,5 @@ function TibiaFiles.init()
end end
end end
function TibiaFiles.terminate() function terminate()
end end

@ -2,10 +2,7 @@ Module
name: game_tibiafiles name: game_tibiafiles
description: Contains tibia spr and dat description: Contains tibia spr and dat
reloadable: false reloadable: false
sandboxed: true
@onLoad: | scripts: [tibiafiles.lua]
dofile 'tibiafiles' @onLoad: init()
TibiaFiles.init() @onUnload: terminate()
@onUnload: |
TibiaFiles.terminate()

@ -1,8 +1,8 @@
MainWindow MainWindow
size: 256 128 size: 256 128
!text: tr('Add to VIP list') !text: tr('Add to VIP list')
@onEnter: VipList.addVip() @onEnter: addVip()
@onEscape: VipList.destroyAddWindow() @onEscape: destroyAddWindow()
Label Label
!text: tr('Please enter a character name:') !text: tr('Please enter a character name:')
@ -29,11 +29,11 @@ MainWindow
anchors.right: next.left anchors.right: next.left
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
margin-right: 10 margin-right: 10
@onClick: VipList.addVip() @onClick: addVip()
Button Button
!text: tr('Cancel') !text: tr('Cancel')
width: 64 width: 64
anchors.right: parent.right anchors.right: parent.right
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
@onClick: VipList.destroyAddWindow() @onClick: destroyAddWindow()

@ -1,53 +1,45 @@
VipList = {} vipWindow = nil
vipButton = nil
addVipWindow = nil
-- private variables function init()
local vipWindow connect(g_game, { onGameEnd = clear,
local vipButton onAddVip = onAddVip,
local addVipWindow onVipStateChange = onVipStateChange })
-- public functions
function VipList.init()
connect(g_game, { onGameEnd = VipList.clear,
onAddVip = VipList.onAddVip,
onVipStateChange = VipList.onVipStateChange })
g_keyboard.bindKeyDown('Ctrl+P', toggle)
g_keyboard.bindKeyDown('Ctrl+P', VipList.toggle) vipWindow = g_ui.loadUI('viplist.otui', modules.game_interface.getRightPanel())
vipButton = TopMenu.addRightGameToggleButton('vipListButton', tr('VIP list') .. ' (Ctrl+P)', 'viplist.png', toggle)
vipWindow = g_ui.loadUI('viplist.otui', GameInterface.getRightPanel())
vipButton = TopMenu.addRightGameToggleButton('vipListButton', tr('VIP list') .. ' (Ctrl+P)', 'viplist.png', VipList.toggle)
vipButton:setOn(true) vipButton:setOn(true)
VipList.refresh() refresh()
end end
function VipList.terminate() function terminate()
g_keyboard.unbindKeyDown('Ctrl+P') g_keyboard.unbindKeyDown('Ctrl+P')
disconnect(g_game, { onGameEnd = VipList.clear, disconnect(g_game, { onGameEnd = clear,
onAddVip = VipList.onAddVip, onAddVip = onAddVip,
onVipStateChange = VipList.onVipStateChange }) onVipStateChange = onVipStateChange })
vipWindow:destroy() vipWindow:destroy()
vipWindow = nil
vipButton:destroy() vipButton:destroy()
vipButton = nil
VipList = nil
end end
function VipList.refresh() function refresh()
VipList.clear() clear()
for id,vip in pairs(g_game.getVips()) do for id,vip in pairs(g_game.getVips()) do
VipList.onAddVip(id, unpack(vip)) onAddVip(id, unpack(vip))
end end
end end
function VipList.clear() function clear()
local vipList = vipWindow:getChildById('contentsPanel') local vipList = vipWindow:getChildById('contentsPanel')
vipList:destroyChildren() vipList:destroyChildren()
end end
function VipList.toggle() function toggle()
if vipButton:isOn() then if vipButton:isOn() then
vipWindow:close() vipWindow:close()
vipButton:setOn(false) vipButton:setOn(false)
@ -57,26 +49,25 @@ function VipList.toggle()
end end
end end
function VipList.onMiniWindowClose() function onMiniWindowClose()
vipButton:setOn(false) vipButton:setOn(false)
end end
function VipList.createAddWindow() function createAddWindow()
addVipWindow = g_ui.displayUI('addvip.otui') addVipWindow = g_ui.displayUI('addvip.otui')
end end
function VipList.destroyAddWindow() function destroyAddWindow()
addVipWindow:destroy() addVipWindow:destroy()
addVipWindow = nil addVipWindow = nil
end end
function VipList.addVip() function addVip()
g_game.addVip(addVipWindow:getChildById('name'):getText()) g_game.addVip(addVipWindow:getChildById('name'):getText())
VipList.destroyAddWindow() destroyAddWindow()
end end
-- hooked events function onAddVip(id, name, online)
function VipList.onAddVip(id, name, online)
local vipList = vipWindow:getChildById('contentsPanel') local vipList = vipWindow:getChildById('contentsPanel')
local label = g_ui.createWidget('VipListLabel') local label = g_ui.createWidget('VipListLabel')
@ -122,34 +113,34 @@ function VipList.onAddVip(id, name, online)
vipList:insertChild(childrenCount+1, label) vipList:insertChild(childrenCount+1, label)
end end
function VipList.onVipStateChange(id, online) function onVipStateChange(id, online)
local vipList = vipWindow:getChildById('contentsPanel') local vipList = vipWindow:getChildById('contentsPanel')
local label = vipList:getChildById('vip' .. id) local label = vipList:getChildById('vip' .. id)
local text = label:getText() local text = label:getText()
label:destroy() label:destroy()
VipList.onAddVip(id, text, online) onAddVip(id, text, online)
end end
function VipList.onVipListMousePress(widget, mousePos, mouseButton) function onVipListMousePress(widget, mousePos, mouseButton)
if mouseButton ~= MouseRightButton then return end if mouseButton ~= MouseRightButton then return end
local vipList = vipWindow:getChildById('contentsPanel') local vipList = vipWindow:getChildById('contentsPanel')
local menu = g_ui.createWidget('PopupMenu') local menu = g_ui.createWidget('PopupMenu')
menu:addOption(tr('Add new VIP'), function() VipList.createAddWindow() end) menu:addOption(tr('Add new VIP'), function() createAddWindow() end)
menu:display(mousePos) menu:display(mousePos)
return true return true
end end
function VipList.onVipListLabelMousePress(widget, mousePos, mouseButton) function onVipListLabelMousePress(widget, mousePos, mouseButton)
if mouseButton ~= MouseRightButton then return end if mouseButton ~= MouseRightButton then return end
local vipList = vipWindow:getChildById('contentsPanel') local vipList = vipWindow:getChildById('contentsPanel')
local menu = g_ui.createWidget('PopupMenu') local menu = g_ui.createWidget('PopupMenu')
menu:addOption(tr('Add new VIP'), function() VipList.createAddWindow() end) menu:addOption(tr('Add new VIP'), function() createAddWindow() end)
menu:addOption(tr('Remove %s', widget:getText()), function() if widget then g_game.removeVip(widget:getId():sub(4)) vipList:removeChild(widget) end end) menu:addOption(tr('Remove %s', widget:getText()), function() if widget then g_game.removeVip(widget:getId():sub(4)) vipList:removeChild(widget) end end)
menu:addSeparator() menu:addSeparator()
menu:addOption(tr('Copy Name'), function() g_window.setClipboardText(widget:getText()) end) menu:addOption(tr('Copy Name'), function() g_window.setClipboardText(widget:getText()) end)

@ -3,10 +3,7 @@ Module
description: Manage vip list window description: Manage vip list window
author: baxnie, edubart author: baxnie, edubart
website: www.otclient.info website: www.otclient.info
sandboxed: true
@onLoad: | scripts: [ viplist.lua ]
dofile 'viplist' @onLoad: init()
VipList.init() @onUnload: terminate()
@onUnload: |
VipList.terminate()

@ -1,17 +1,17 @@
VipListLabel < GameLabel VipListLabel < GameLabel
font: verdana-11px-monochrome font: verdana-11px-monochrome
phantom: false phantom: false
&onMousePress: VipList.onVipListLabelMousePress &onMousePress: onVipListLabelMousePress
MiniWindow MiniWindow
id: vipWindow id: vipWindow
!text: tr('VIP List') !text: tr('VIP List')
height: 100 height: 100
icon: viplist.png icon: viplist.png
@onClose: VipList.onMiniWindowClose() @onClose: onMiniWindowClose()
&save: true &save: true
MiniWindowContents MiniWindowContents
layout: verticalBox layout: verticalBox
anchors.fill: parent anchors.fill: parent
&onMousePress: VipList.onVipListMousePress &onMousePress: onVipListMousePress

@ -70,6 +70,13 @@ bool Module::load()
if(m_sandboxed) if(m_sandboxed)
g_lua.resetGlobalEnvironment(); g_lua.resetGlobalEnvironment();
// add to package.loaded
g_lua.getGlobalField("package", "loaded");
g_lua.getRef(m_sandboxEnv);
g_lua.setField(m_name);
g_lua.pop();
m_loaded = true;
g_logger.debug(stdext::format("Loaded module '%s'", m_name)); g_logger.debug(stdext::format("Loaded module '%s'", m_name));
} catch(stdext::exception& e) { } catch(stdext::exception& e) {
if(m_sandboxed) if(m_sandboxed)
@ -78,7 +85,6 @@ bool Module::load()
return false; return false;
} }
m_loaded = true;
g_modules.updateModuleLoadOrder(asModule()); g_modules.updateModuleLoadOrder(asModule());
for(const std::string& modName : m_loadLaterModules) { for(const std::string& modName : m_loadLaterModules) {
@ -119,6 +125,12 @@ void Module::unload()
g_lua.clearTable(); g_lua.clearTable();
g_lua.pop(); g_lua.pop();
// remove from package.loaded
g_lua.getGlobalField("package", "loaded");
g_lua.pushNil();
g_lua.setField(m_name);
g_lua.pop();
m_loaded = false; m_loaded = false;
//g_logger.info(stdext::format("Unloaded module '%s'", m_name)); //g_logger.info(stdext::format("Unloaded module '%s'", m_name));
g_modules.updateModuleLoadOrder(asModule()); g_modules.updateModuleLoadOrder(asModule());

@ -930,18 +930,21 @@ void LuaInterface::setTable(int index)
void LuaInterface::clearTable(int index) void LuaInterface::clearTable(int index)
{ {
assert(hasIndex(index) && isTable(index)); assert(hasIndex(index) && isTable(index));
pushNil(); pushNil(); // table, nil
bool stop = false; bool stop = false;
while(!stop && next(index-1)) { while(next(index-1)) { // table, key, value
pop(); pop(); // table, key
pushValue(); pushValue(); // table, key, key
if(next(index-2)) if(next(index-2)) { // table, key, nextkey, value
pop(); pop(); // table, key, nextkey
else insert(-2); // table, nextkey, key
stop = true; pushNil(); // table, nextkey, key, nil
insert(-2); rawSet(index-3); // table, nextkey
pushNil(); } else { // table, key
rawSet(index-3); pushNil(); // table, key, nil
rawSet(index-2); // table
break;
}
} }
} }

@ -191,10 +191,8 @@ void OTMLParser::parseNode(const std::string& data)
if(boost::starts_with(value, "[") && boost::ends_with(value, "]")) { if(boost::starts_with(value, "[") && boost::ends_with(value, "]")) {
std::string tmp = value.substr(1, value.length()-2); std::string tmp = value.substr(1, value.length()-2);
boost::tokenizer<boost::escaped_list_separator<char>> tokens(tmp); boost::tokenizer<boost::escaped_list_separator<char>> tokens(tmp);
for(std::string v : tokens) { for(std::string v : tokens)
stdext::trim(v); node->writeIn(stdext::trim(v));
node->writeIn(v);
}
} else } else
node->setValue(value); node->setValue(value);
} }

Loading…
Cancel
Save