diff --git a/modules/game/thing.lua b/modules/game/thing.lua index 8c4864f9..c08b5bc6 100644 --- a/modules/game/thing.lua +++ b/modules/game/thing.lua @@ -3,13 +3,24 @@ function Game.processMouseAction(menuPosition, mouseButton, autoWalk, lookThing, useThing, creatureThing, multiUseThing) local keyboardModifiers = g_window.getKeyboardModifiers() - if autoWalk and keyboardModifiers == KeyboardNoModifier and mouseButton == MouseLeftButton then + local selectedThing = Game.getSelectedThing() + if mouseButton == MouseRightButton and selectedThing then + Game.setSelectedThing(nil) + return true + end + + if autoWalk and keyboardModifiers == KeyboardNoModifier and mouseButton == MouseLeftButton and not Game.getSelectedThing() then -- todo auto walk return true end if not Options.classicControl then - if keyboardModifiers == KeyboardNoModifier and mouseButton == MouseRightButton then + if mouseButton == MouseLeftButton and selectedThing then + Game.useWith(Game.getSelectedThing(), useThing) + Game.setSelectedThing(nil) + -- restore cursor + return true + elseif keyboardModifiers == KeyboardNoModifier and mouseButton == MouseRightButton then Game.createThingMenu(menuPosition, lookThing, useThing, creatureThing) return true elseif lookThing and keyboardModifiers == KeyboardShiftModifier and (mouseButton == MouseLeftButton or mouseButton == MouseRightButton) then @@ -19,7 +30,8 @@ function Game.processMouseAction(menuPosition, mouseButton, autoWalk, lookThing, if useThing:isContainer() then print "open" elseif useThing:isMultiUse() then - print "use with..." + Game.setSelectedThing(useThing) + -- todo change cursor else Game.use(useThing) end @@ -29,13 +41,19 @@ function Game.processMouseAction(menuPosition, mouseButton, autoWalk, lookThing, return true end else - if multiUseThing and keyboardModifiers == KeyboardNoModifier and mouseButton == MouseRightButton then + if mouseButton == MouseLeftButton and selectedThing then + Game.useWith(Game.getSelectedThing(), multiUseThing) + Game.setSelectedThing(nil) + -- restore cursor + return true + elseif multiUseThing and keyboardModifiers == KeyboardNoModifier and mouseButton == MouseRightButton then if multiUseThing:asCreature() then Game.attack(multiUseThing:asCreature()) elseif multiUseThing:isContainer() then print "open" elseif multiUseThing:isMultiUse() then - print "use with..." + Game.setSelectedThing(multiUseThing) + -- todo change cursor else Game.use(useThing) end @@ -70,7 +88,8 @@ function Game.createThingMenu(menuPosition, lookThing, useThing, creatureThing) menu:addOption('Open', function() print('open') end) else if useThing:isMultiUse() then - menu:addOption('Use with ...', function() print('use with...') end) + -- todo change cursor + menu:addOption('Use with ...', function() Game.setSelectedThing(useThing) end) else menu:addOption('Use', function() Game.use(useThing) end) end diff --git a/src/otclient/core/game.cpp b/src/otclient/core/game.cpp index 82e9e583..62f5607e 100644 --- a/src/otclient/core/game.cpp +++ b/src/otclient/core/game.cpp @@ -37,6 +37,7 @@ void Game::loginWorld(const std::string& account, const std::string& password, c m_online = false; m_dead = false; m_walkFeedback = true; + m_selectedThing = nullptr; m_walkPing = 0; m_protocolGame = ProtocolGamePtr(new ProtocolGame); m_protocolGame->login(account, password, worldHost, (uint16)worldPort, characterName); @@ -251,6 +252,16 @@ void Game::use(const ThingPtr& thing) m_protocolGame->sendUseItem(thing->getPos(), thing->getId(), stackpos, 0);// last 0 has something to do with container } +void Game::useWith(const ThingPtr& fromThing, const ThingPtr& toThing) +{ + if(!m_online || !fromThing || !toThing || !checkBotProtection()) + return; + + int fromStackpos = getThingStackpos(fromThing), toStackpos = getThingStackpos(toThing); + if(fromStackpos != -1 && toStackpos != -1) + m_protocolGame->sendUseItemEx(fromThing->getPos(), fromThing->getId(), fromStackpos, toThing->getPos(), toThing->getId(), toStackpos); +} + void Game::attack(const CreaturePtr& creature) { if(!m_online || !creature || !checkBotProtection()) diff --git a/src/otclient/core/game.h b/src/otclient/core/game.h index 4e1a1bc9..218de49b 100644 --- a/src/otclient/core/game.h +++ b/src/otclient/core/game.h @@ -57,6 +57,7 @@ public: void turn(Otc::Direction direction); void look(const ThingPtr& thing); void use(const ThingPtr& thing); + void useWith(const ThingPtr& fromThing, const ThingPtr& toThing); void attack(const CreaturePtr& creature); void cancelAttack(); void follow(const CreaturePtr& creature); @@ -82,6 +83,9 @@ public: bool isOnline() { return m_online; } bool isDead() { return m_dead; } + void setSelectedThing(const ThingPtr& thing) { m_selectedThing = thing; } + ThingPtr getSelectedThing() { return m_selectedThing; } + void setServerBeat(int serverBeat) { m_serverBeat = serverBeat; } int getServerBeat() { return m_serverBeat; } @@ -101,6 +105,7 @@ private: Timer m_walkPingTimer; int m_walkPing; int m_serverBeat; + ThingPtr m_selectedThing; }; extern Game g_game; diff --git a/src/otclient/luafunctions.cpp b/src/otclient/luafunctions.cpp index a13d4f8b..ce0020ca 100644 --- a/src/otclient/luafunctions.cpp +++ b/src/otclient/luafunctions.cpp @@ -179,6 +179,7 @@ void OTClient::registerLuaFunctions() g_lua.bindClassStaticFunction("setOutfit", std::bind(&Game::setOutfit, &g_game, _1)); g_lua.bindClassStaticFunction("look", std::bind(&Game::look, &g_game, _1)); g_lua.bindClassStaticFunction("use", std::bind(&Game::use, &g_game, _1)); + g_lua.bindClassStaticFunction("useWith", std::bind(&Game::useWith, &g_game, _1, _2)); g_lua.bindClassStaticFunction("attack", std::bind(&Game::attack, &g_game, _1)); g_lua.bindClassStaticFunction("cancelAttack", std::bind(&Game::cancelAttack, &g_game)); g_lua.bindClassStaticFunction("follow", std::bind(&Game::follow, &g_game, _1)); @@ -199,6 +200,8 @@ void OTClient::registerLuaFunctions() g_lua.bindClassStaticFunction("talkPrivate", std::bind(&Game::talkPrivate, &g_game, _1, _2, _3)); g_lua.bindClassStaticFunction("getLocalPlayer", std::bind(&Game::getLocalPlayer, &g_game)); g_lua.bindClassStaticFunction("getProtocolVersion", std::bind(&Game::getProtocolVersion, &g_game)); + g_lua.bindClassStaticFunction("setSelectedThing", std::bind(&Game::setSelectedThing, &g_game, _1)); + g_lua.bindClassStaticFunction("getSelectedThing", std::bind(&Game::getSelectedThing, &g_game)); g_lua.registerClass(); g_lua.bindClassStaticFunction("create", []{ return UIItemPtr(new UIItem); } );