Changed: #1433 Merge changes from patch 1.13

hg/feature/gsoc2012-fabien
kervala 13 years ago
parent 17aded8877
commit 86eaabd0a2

@ -358,17 +358,8 @@ CCharacterCL::CCharacterCL()
_EventFactionId = 0; _EventFactionId = 0;
_PvpMode = PVP_MODE::None; _PvpMode = PVP_MODE::None;
_PvpClan = PVP_CLAN::None;
for (uint8 i = 0; i < PVP_CLAN::NbClans; i++)
{
_PvpAllies[i] = false;
_PvpEnemies[i] = false;
}
_ClanCivMaxFame = PVP_CLAN::None;
_ClanCultMaxFame = PVP_CLAN::None;
_LeagueId = 0;
_OutpostId = 0; _OutpostId = 0;
_OutpostSide = OUTPOSTENUMS::UnknownPVPSide; _OutpostSide = OUTPOSTENUMS::UnknownPVPSide;
@ -1842,9 +1833,30 @@ void CCharacterCL::updateVisualPropertyGuildNameID(const NLMISC::TGameCycle &/*
//----------------------------------------------- //-----------------------------------------------
void CCharacterCL::updateVisualPropertyEventFactionID(const NLMISC::TGameCycle &/* gameCycle */, const sint64 &prop) void CCharacterCL::updateVisualPropertyEventFactionID(const NLMISC::TGameCycle &/* gameCycle */, const sint64 &prop)
{ {
_EventFactionId = uint32(prop); // ODD Hack by Ulukyn
//_EventFactionId = uint32(prop);
_PvpMode = uint32(prop);
buildInSceneInterface(); buildInSceneInterface();
if (isUser())
{
uint i;
uint numEntity = (uint)EntitiesMngr.entities().size();
for (i=0; i<numEntity; i++)
{
CEntityCL *entity = EntitiesMngr.entity(i);
if (entity)
{
CCharacterCL *character = dynamic_cast<CCharacterCL*>(entity);
if (character)
{
if( character->getPvpMode() != 0 && !character->isUser())
character->buildInSceneInterface ();
}
}
}
}
} // updateVisualPropertyEventFactionID // } // updateVisualPropertyEventFactionID //
//----------------------------------------------- //-----------------------------------------------
@ -1853,8 +1865,8 @@ void CCharacterCL::updateVisualPropertyEventFactionID(const NLMISC::TGameCycle &
//----------------------------------------------- //-----------------------------------------------
void CCharacterCL::updateVisualPropertyPvpMode(const NLMISC::TGameCycle &/* gameCycle */, const sint64 &prop) void CCharacterCL::updateVisualPropertyPvpMode(const NLMISC::TGameCycle &/* gameCycle */, const sint64 &prop)
{ {
_PvpMode = (uint8)prop; //_PvpMode = uint32(prop);
buildInSceneInterface(); //buildInSceneInterface();
} // updateVisualPropertyPvpMode // } // updateVisualPropertyPvpMode //
@ -1864,18 +1876,27 @@ void CCharacterCL::updateVisualPropertyPvpMode(const NLMISC::TGameCycle &/* game
//----------------------------------------------- //-----------------------------------------------
void CCharacterCL::updateVisualPropertyPvpClan(const NLMISC::TGameCycle &/* gameCycle */, const sint64 &prop) void CCharacterCL::updateVisualPropertyPvpClan(const NLMISC::TGameCycle &/* gameCycle */, const sint64 &prop)
{ {
// get fames signs from prop _LeagueId = uint32(prop);
for (uint8 fameIdx = 0; fameIdx < 7; fameIdx++)
{
_PvpAllies[fameIdx] = (prop & (SINT64_CONSTANT(1) << (2*fameIdx))) != 0;
_PvpEnemies[fameIdx] = (prop & (SINT64_CONSTANT(1) << (2*fameIdx+1))) != 0;
}
_ClanCivMaxFame = PVP_CLAN::TPVPClan((prop & (0x03 << 2*7)) >> 2*7);
_ClanCultMaxFame = PVP_CLAN::TPVPClan(4 + ((prop & (0x03 << 2*8)) >> 2*8));
buildInSceneInterface(); buildInSceneInterface();
if (isUser())
{
uint i;
uint numEntity = (uint)EntitiesMngr.entities().size();
for (i=0; i<numEntity; i++)
{
CEntityCL *entity = EntitiesMngr.entity(i);
if (entity)
{
CCharacterCL *character = dynamic_cast<CCharacterCL*>(entity);
if (character)
{
if( character->getPvpMode() != 0 && !character->isUser())
character->buildInSceneInterface ();
}
}
}
}
} // updateVisualPropertyPvpClan // } // updateVisualPropertyPvpClan //
//----------------------------------------------- //-----------------------------------------------
@ -4522,10 +4543,6 @@ void CCharacterCL::applyBehaviourFlyingHPs(const CBehaviourContext &bc, const MB
else else
deltaHPColor = ClientCfg.SystemInfoParams["dg"].Color; deltaHPColor = ClientCfg.SystemInfoParams["dg"].Color;
} }
else
{
deltaHPColor = CRGBA(127,127,127);
}
} }
else else
{ {
@ -10252,7 +10269,7 @@ NLMISC_COMMAND(pvpMode, "modify pvp mode", "[<pvp mode> <state>]")
if( args.size() == 0 ) if( args.size() == 0 )
{ {
uint8 pvpMode = playerTarget->getPvpMode(); uint16 pvpMode = playerTarget->getPvpMode();
string str; string str;
if( pvpMode&PVP_MODE::PvpDuel ) if( pvpMode&PVP_MODE::PvpDuel )
str+="duel "; str+="duel ";
@ -10270,6 +10287,10 @@ NLMISC_COMMAND(pvpMode, "modify pvp mode", "[<pvp mode> <state>]")
str+="faction "; str+="faction ";
if( pvpMode&PVP_MODE::PvpFactionFlagged) if( pvpMode&PVP_MODE::PvpFactionFlagged)
str+="faction_flagged "; str+="faction_flagged ";
if( pvpMode&PVP_MODE::PvpZoneSafe)
str+="in_safe_zone ";
if( pvpMode&PVP_MODE::PvpSafe)
str+="safe ";
IM->displaySystemInfo(ucstring(str)); IM->displaySystemInfo(ucstring(str));
nlinfo("<pvpMode> %s",str.c_str()); nlinfo("<pvpMode> %s",str.c_str());
} }
@ -10280,14 +10301,14 @@ NLMISC_COMMAND(pvpMode, "modify pvp mode", "[<pvp mode> <state>]")
fromString(args[1], state); fromString(args[1], state);
if( state ) if( state )
{ {
uint8 currentPVPMode = playerTarget->getPvpMode(); uint16 currentPVPMode = playerTarget->getPvpMode();
currentPVPMode |= pvpMode; currentPVPMode |= pvpMode;
playerTarget->setPvpMode(currentPVPMode); playerTarget->setPvpMode(currentPVPMode);
IM->displaySystemInfo(toString("<pvpMode> adding pvp mode %s",args[0].c_str())); IM->displaySystemInfo(toString("<pvpMode> adding pvp mode %s",args[0].c_str()));
} }
else else
{ {
uint8 currentPVPMode = playerTarget->getPvpMode(); uint16 currentPVPMode = playerTarget->getPvpMode();
currentPVPMode &= ~pvpMode; currentPVPMode &= ~pvpMode;
playerTarget->setPvpMode(currentPVPMode); playerTarget->setPvpMode(currentPVPMode);
IM->displaySystemInfo(toString("<pvpMode> removing pvp mode %s",args[0].c_str())); IM->displaySystemInfo(toString("<pvpMode> removing pvp mode %s",args[0].c_str()));
@ -10297,7 +10318,7 @@ NLMISC_COMMAND(pvpMode, "modify pvp mode", "[<pvp mode> <state>]")
return true; return true;
} }
/*
NLMISC_COMMAND(pvpClan, "modify pvp clan", "<pvp clan>") NLMISC_COMMAND(pvpClan, "modify pvp clan", "<pvp clan>")
{ {
if (args.size() != 1) return false; if (args.size() != 1) return false;
@ -10319,13 +10340,13 @@ NLMISC_COMMAND(pvpClan, "modify pvp clan", "<pvp clan>")
if (!playerTarget) if (!playerTarget)
return false; return false;
PVP_CLAN::TPVPClan clan = PVP_CLAN::fromString(args[0]); // PVP_CLAN::TPVPClan clan = PVP_CLAN::fromString(args[0]);
playerTarget->setPvpClan(clan); // playerTarget->setPvpClan(clan);
playerTarget->buildInSceneInterface(); playerTarget->buildInSceneInterface();
return true; return true;
} }
*/
#endif // !FINAL_VERSION #endif // !FINAL_VERSION
#include "r2/editor.h" #include "r2/editor.h"

@ -84,7 +84,7 @@ public:
enum { MaxNumAura = 2 }; enum { MaxNumAura = 2 };
enum TAtkHeight enum TAtkHeight
{ {
AtkUnknownHeight = 0, AtkUnkownHeight = 0,
AtkLow, AtkLow,
AtkMiddle, AtkMiddle,
AtkHigh AtkHigh
@ -368,48 +368,10 @@ public:
virtual uint64 getGuildSymbol () const { return _GuildSymbol; } virtual uint64 getGuildSymbol () const { return _GuildSymbol; }
virtual uint32 getEventFactionID() const { return _EventFactionId; } virtual uint32 getEventFactionID() const { return _EventFactionId; }
virtual uint8 getPvpMode() const { return _PvpMode; } virtual uint16 getPvpMode() const { return _PvpMode; }
void setPvpMode(uint8 mode) { _PvpMode=mode; } void setPvpMode(uint16 mode) { _PvpMode=mode; }
virtual PVP_CLAN::TPVPClan getPvpClan() const { return _PvpClan; } virtual uint32 getLeagueID() const { return _LeagueId; }
void setPvpClan(PVP_CLAN::TPVPClan clan) { _PvpClan=clan; } void setLeagueID(uint32 league) { _LeagueId=league; }
virtual PVP_CLAN::TPVPClan getClanCivMaxFame() const { return _ClanCivMaxFame; }
void setClanCivMaxFame(PVP_CLAN::TPVPClan clan) { _ClanCivMaxFame=clan; }
virtual PVP_CLAN::TPVPClan getClanCultMaxFame() const { return _ClanCultMaxFame; }
void setClanCultMaxFame(PVP_CLAN::TPVPClan clan) { _ClanCultMaxFame=clan; }
virtual bool isPvpAlly(uint8 faction) const { if (faction < PVP_CLAN::NbClans) return _PvpAllies[faction]; else return false; }
virtual bool isPvpEnnemy(uint8 faction) const { if (faction < PVP_CLAN::NbClans) return _PvpEnemies[faction]; else return false; }
virtual bool isPvpMarauder() const
{
for (uint8 i = 0; i < 4; i++)
if (!_PvpEnemies[i])
return false;
return true;
}
virtual bool isPvpTrytonist() const
{
if (_PvpEnemies[4] && _PvpEnemies[6])
return true;
return false;
}
virtual bool isPvpPrimas() const
{
if (_PvpAllies[4] && _PvpAllies[6])
return true;
return false;
}
virtual bool isPvpRanger() const
{
for (uint8 i = 0; i < 4; i++)
if (!_PvpAllies[i])
return false;
return true;
}
virtual uint16 getOutpostId() const { return _OutpostId; } virtual uint16 getOutpostId() const { return _OutpostId; }
virtual OUTPOSTENUMS::TPVPSide getOutpostSide() const { return _OutpostSide; } virtual OUTPOSTENUMS::TPVPSide getOutpostSide() const { return _OutpostSide; }
@ -727,12 +689,9 @@ protected:
uint32 _GuildNameId; uint32 _GuildNameId;
uint64 _GuildSymbol; uint64 _GuildSymbol;
uint32 _EventFactionId; uint32 _EventFactionId;
uint8 _PvpMode; uint16 _PvpMode;
PVP_CLAN::TPVPClan _PvpClan; PVP_CLAN::TPVPClan _PvpClan;
PVP_CLAN::TPVPClan _ClanCivMaxFame; uint32 _LeagueId;
PVP_CLAN::TPVPClan _ClanCultMaxFame;
bool _PvpAllies[PVP_CLAN::NbClans];
bool _PvpEnemies[PVP_CLAN::NbClans];
uint16 _OutpostId; uint16 _OutpostId;
OUTPOSTENUMS::TPVPSide _OutpostSide; OUTPOSTENUMS::TPVPSide _OutpostSide;

@ -422,15 +422,12 @@ int main(int argc, char **argv)
string sCmdLine = cmdline; string sCmdLine = cmdline;
#if FINAL_VERSION #if FINAL_VERSION
if (sCmdLine.find("/multi") == string::npos) // If '/multi' not found //if (sCmdLine.find("/multi") == string::npos) // If '/multi' not found
{ //{
HANDLE mutex = CreateMutex (NULL, false, "RyzomClient"); // HANDLE mutex = CreateMutex (NULL, false, "RyzomClient");
if (mutex && GetLastError() == ERROR_ALREADY_EXISTS) // if (mutex && GetLastError() == ERROR_ALREADY_EXISTS)
{ // exit (0);
delete appContext; //}
return 0;
}
}
initCrashReport (); initCrashReport ();
#endif // FINAL_VERSION #endif // FINAL_VERSION

@ -424,6 +424,7 @@ CClientConfig::CClientConfig()
PatchWanted = false; PatchWanted = false;
#endif #endif
PatchUrl = ""; PatchUrl = "";
PatchletUrl = "";
PatchVersion = ""; PatchVersion = "";
PatchServer = ""; PatchServer = "";
@ -433,6 +434,7 @@ CClientConfig::CClientConfig()
RingReleaseNotePath = "http://"+WebIgMainDomain+"/releasenotes_ring/index.php"; RingReleaseNotePath = "http://"+WebIgMainDomain+"/releasenotes_ring/index.php";
ReleaseNotePath = "http://"+WebIgMainDomain+"/releasenotes/index.php"; ReleaseNotePath = "http://"+WebIgMainDomain+"/releasenotes/index.php";
/////////////// ///////////////
// ANIMATION // // ANIMATION //
// With a bigger angle, rotation is animated. // With a bigger angle, rotation is animated.
@ -1044,9 +1046,13 @@ void CClientConfig::setValues()
READ_STRING_DEV(ReleaseNotePath) READ_STRING_DEV(ReleaseNotePath)
READ_STRING_FV(PatchServer) READ_STRING_FV(PatchServer)
/////////////////////////
// NEW PATCHLET SYSTEM //
READ_STRING_FV(PatchletUrl)
//////////////////////// ////////////////////////
// WEBIG // // WEBIG //
READ_STRING_DEV(WebIgMainDomain); READ_STRING_FV(WebIgMainDomain);
READ_STRINGVECTOR_FV(WebIgTrustedDomains); READ_STRINGVECTOR_FV(WebIgTrustedDomains);
/////////////// ///////////////

@ -286,17 +286,17 @@ struct CClientConfig
// NEW PATCHING SYSTEM // // NEW PATCHING SYSTEM //
bool PatchWanted; bool PatchWanted;
std::string PatchUrl; std::string PatchUrl;
std::string PatchletUrl;
std::string PatchVersion; std::string PatchVersion;
std::string PatchServer; std::string PatchServer;
std::string RingReleaseNotePath; std::string RingReleaseNotePath;
std::string ReleaseNotePath; std::string ReleaseNotePath;
////////////////////////
// WEBIG //
std::string WebIgMainDomain; std::string WebIgMainDomain;
std::vector<string> WebIgTrustedDomains; std::vector<string> WebIgTrustedDomains;
/////////////// ///////////////
// ANIMATION // // ANIMATION //
// With a bigger angle, rotation is animated. // With a bigger angle, rotation is animated.

@ -963,16 +963,10 @@ void CClientChatManager::buildTellSentence(const ucstring &sender, const ucstrin
else else
{ {
// Does the char have a CSR title? // Does the char have a CSR title?
if (CHARACTER_TITLE::isCsrTitle(CEntityCL::getTitleFromName(sender))) csr = ucstring("(CSR) "); csr = CHARACTER_TITLE::isCsrTitle(CEntityCL::getTitleFromName(sender)) ? ucstring("(CSR) ") : ucstring("");
} }
ucstring cur_time; result = csr + name + ucstring(" ") + CI18N::get("tellsYou") + ucstring(": ") + msg;
CCDBNodeLeaf *pNL = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false);
if (pNL && pNL->getValueBool())
{
cur_time = CInterfaceManager::getTimestampHuman();
}
result = cur_time + csr + name + ucstring(" ") + CI18N::get("tellsYou") + ucstring(": ") + msg;
} }
} }
@ -1002,23 +996,18 @@ void CClientChatManager::buildChatSentence(TDataSetIndex /* compressedSenderInde
if (!catStr.empty()) if (!catStr.empty())
cat = string("&")+catStr+"&"; cat = string("&")+catStr+"&";
// Format the sentence with the provided sender name if ( ! cat.empty())
ucstring senderName = CEntityCL::removeTitleAndShardFromName(sender);
// Add time if not a &bbl&
ucstring cur_time;
if (cat.toString() != "&bbl&")
{ {
CCDBNodeLeaf *pNL = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false); result = msg;
if (pNL && pNL->getValueBool()) return;
{
cur_time = CInterfaceManager::getTimestampHuman();
}
} }
// Format the sentence with the provided sender name
ucstring senderName = CEntityCL::removeTitleAndShardFromName(sender);
ucstring csr; ucstring csr;
// Does the char have a CSR title? // Does the char have a CSR title?
if (CHARACTER_TITLE::isCsrTitle(CEntityCL::getTitleFromName(sender))) csr = ucstring("(CSR) "); csr = CHARACTER_TITLE::isCsrTitle(CEntityCL::getTitleFromName(sender)) ? ucstring("(CSR) ") : ucstring("");
if (UserEntity && senderName == UserEntity->getDisplayName()) if (UserEntity && senderName == UserEntity->getDisplayName())
{ {
@ -1026,10 +1015,10 @@ void CClientChatManager::buildChatSentence(TDataSetIndex /* compressedSenderInde
switch(type) switch(type)
{ {
case CChatGroup::shout: case CChatGroup::shout:
result = cat + cur_time + csr + CI18N::get("youShout") + ucstring(": ") + finalMsg; result = cat + csr + CI18N::get("youShout") + ucstring(": ") + finalMsg;
break; break;
default: default:
result = cat + cur_time + csr + CI18N::get("youSay") + ucstring(": ") + finalMsg; result = cat + csr + CI18N::get("youSay") + ucstring(": ") + finalMsg;
break; break;
} }
} }
@ -1048,10 +1037,10 @@ void CClientChatManager::buildChatSentence(TDataSetIndex /* compressedSenderInde
switch(type) switch(type)
{ {
case CChatGroup::shout: case CChatGroup::shout:
result = cat + cur_time + csr + senderName + ucstring(" ") + CI18N::get("heShout") + ucstring(": ") + finalMsg; result = cat + csr + senderName + ucstring(" ") + CI18N::get("heShout") + ucstring(": ") + finalMsg;
break; break;
default: default:
result = cat + cur_time + csr + senderName + ucstring(" ") + CI18N::get("heSays") + ucstring(": ") + finalMsg; result = cat + csr + senderName + ucstring(" ") + CI18N::get("heSays") + ucstring(": ") + finalMsg;
break; break;
} }
} }
@ -1185,14 +1174,8 @@ class CHandlerTell : public IActionHandler
ucstring finalMsg; ucstring finalMsg;
CChatWindow::encodeColorTag(prop.getRGBA(), finalMsg, false); CChatWindow::encodeColorTag(prop.getRGBA(), finalMsg, false);
ucstring cur_time; ucstring csr = CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw()) ? "(CSR) " : "";
CCDBNodeLeaf *pNL = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false); finalMsg += csr + CI18N::get("youTell") + ": ";
if (pNL && pNL->getValueBool())
cur_time = CInterfaceManager::getTimestampHuman();
ucstring csr;
if (CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw())) csr += ucstring("(CSR) ");
finalMsg += cur_time + csr + CI18N::get("youTell") + ": ";
prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," "); prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," ");
CChatWindow::encodeColorTag(prop.getRGBA(), finalMsg, true); CChatWindow::encodeColorTag(prop.getRGBA(), finalMsg, true);
finalMsg += message; finalMsg += message;
@ -1351,8 +1334,18 @@ class CHandlerTalk : public IActionHandler
{ {
string str = text.toUtf8(); string str = text.toUtf8();
string cmdWithArgs = str.substr(1); string cmdWithArgs = str.substr(1);
/* In the chat context, only ' ' is a possible separator */
// Get the command name from the string, can contain spaces
string cmd = cmdWithArgs.substr(0, cmdWithArgs.find(' ')); string cmd = cmdWithArgs.substr(0, cmdWithArgs.find(' '));
if (cmdWithArgs.find('"') == 0)
{
string::size_type pos = cmdWithArgs.find('"', 1);
if (string::npos != pos)
{
cmd = cmdWithArgs.substr(1, pos - 1);
}
}
if ( NLMISC::ICommand::exists( cmd ) ) if ( NLMISC::ICommand::exists( cmd ) )
{ {
NLMISC::ICommand::execute( cmdWithArgs, g_log ); NLMISC::ICommand::execute( cmdWithArgs, g_log );

@ -192,7 +192,7 @@ NLMISC_COMMAND(where, "Ask information on the position", "")
return false; return false;
} }
NLMISC_COMMAND(who, "Display all players currently in game","[<options (GM)>]") NLMISC_COMMAND(who, "Display all players currently in region","[<options (GM, channel name)>]")
{ {
// Check parameters. // Check parameters.
if(args.size() > 1) if(args.size() > 1)
@ -1177,7 +1177,7 @@ NLMISC_COMMAND(db, "Modify Database","<Property> <Value>")
if(node) if(node)
node->setValue64(value); node->setValue64(value);
else else
pIM->displaySystemInfo(toString("DB %s don't exist.", args[0].c_str())); pIM->displaySystemInfo(toString("DB '%s' does not exist.", args[0].c_str()));
#else #else
pIM->displaySystemInfo(ucstring("Can't write to DB when in Final Version.")); pIM->displaySystemInfo(ucstring("Can't write to DB when in Final Version."));
#endif #endif
@ -1193,7 +1193,7 @@ NLMISC_COMMAND(db, "Modify Database","<Property> <Value>")
nlinfo("%s", str.c_str()); nlinfo("%s", str.c_str());
} }
else else
pIM->displaySystemInfo(toString("DB %s don't exist.", args[0].c_str())); pIM->displaySystemInfo(toString("DB '%s' does not exist.", args[0].c_str()));
return true; return true;
} }
else else
@ -1295,6 +1295,24 @@ NLMISC_COMMAND(setItemName, "set name of items, sbrick, etc..","<sheet_id> <name
} }
NLMISC_COMMAND(setMissingDynstringText, "set text of missing dynamic string"," <name> <text>")
{
if (args.size() < 2) return false;
ucstring name;
name.fromUtf8(args[0]);
ucstring text;
text.fromUtf8(args[1]);
STRING_MANAGER::CStringManagerClient *pSMC = STRING_MANAGER::CStringManagerClient::instance();
if (pSMC)
pSMC->replaceDynString(name, text);
else
return false;
return true;
}
///////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////
@ -5243,7 +5261,7 @@ bool CUserCommand::execute(const std::string &/* rawCommandString */, const std:
{ {
if ((uint)index >= args.size()) if ((uint)index >= args.size())
{ {
// Not enough argument // Not enough arguments
pIM->displaySystemInfo (ucstring(CommandName+" : ")+CI18N::get ("uiCommandWrongArgumentCount")); pIM->displaySystemInfo (ucstring(CommandName+" : ")+CI18N::get ("uiCommandWrongArgumentCount"));
return false; return false;
} }
@ -5253,11 +5271,18 @@ bool CUserCommand::execute(const std::string &/* rawCommandString */, const std:
finalArgs += /*ucstring(*/args[index++]/*).toUtf8()*/; finalArgs += /*ucstring(*/args[index++]/*).toUtf8()*/;
else else
{ {
finalArgs += /*ucstring(*/args[index++]/*).toUtf8()*/;
while (index<args.size()) while (index<args.size())
{ {
finalArgs += " "; finalArgs += (index > 0) ? " " : "";
finalArgs += /*ucstring(*/args[index++]/*).toUtf8()*/; // If arg contains spaces then put it in quotes
if (string::npos != args[index].find(" "))
{
finalArgs += "\"" + args[index++] + "\"";
}
else
{
finalArgs += args[index++];
}
} }
} }
} }

@ -244,20 +244,20 @@ class CAHOnReloadTestPage: public IActionHandler
REGISTER_ACTION_HANDLER (CAHOnReloadTestPage, "on_reload_test_page"); REGISTER_ACTION_HANDLER (CAHOnReloadTestPage, "on_reload_test_page");
//void initWebBrowser() void initWebBrowser()
//{ {
// CInterfaceManager *pIM = CInterfaceManager::getInstance(); CInterfaceManager *pIM = CInterfaceManager::getInstance();
// pIM->getDbProp("UI:VARIABLES:SCREEN")->setValue32(UI_VARIABLES_SCREEN_WEBSTART); //pIM->getDbProp("UI:VARIABLES:SCREEN")->setValue32(UI_VARIABLES_SCREEN_WEBSTART);
//
// // start the browser // start the browser
// CGroupHTML *pGH = dynamic_cast<CGroupHTML*>(pIM->getElementFromId(GROUP_BROWSER)); CGroupHTML *pGH = dynamic_cast<CGroupHTML*>(pIM->getElementFromId(GROUP_BROWSER));
//
// if (pGH) if (pGH)
// { {
// pGH->setActive(true); pGH->setActive(true);
// pGH->browse(MainPageURL.c_str()); pGH->browse(ClientCfg.PatchletUrl.c_str());
// } }
//} }
// ------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------
@ -392,9 +392,6 @@ bool connection (const string &cookie, const string &fsaddr)
pIM->getDbProp ("UI:CURRENT_SCREEN")->setValue32(ClientCfg.Local ? 6 : -1); // TMP TMP pIM->getDbProp ("UI:CURRENT_SCREEN")->setValue32(ClientCfg.Local ? 6 : -1); // TMP TMP
CCDBNodeBranch::flushObserversCalls(); CCDBNodeBranch::flushObserversCalls();
// Init web box
//initWebBrowser();
// Active inputs // Active inputs
Actions.enable(true); Actions.enable(true);
EditActions.enable(true); EditActions.enable(true);
@ -422,6 +419,10 @@ bool connection (const string &cookie, const string &fsaddr)
nlinfo ("PROFILE: %d seconds for connection", (uint32)(ryzomGetLocalTime ()-connStart)/1000); nlinfo ("PROFILE: %d seconds for connection", (uint32)(ryzomGetLocalTime ()-connStart)/1000);
// Init web box
nlinfo("ok");
initWebBrowser();
// TMP TMP // TMP TMP
if (ClientCfg.Local) if (ClientCfg.Local)
{ {

@ -484,6 +484,9 @@ void checkUnderCursor()
if(ContextCur.context("ATTACK")) if(ContextCur.context("ATTACK"))
return; return;
} }
if(testMissionOption(0))
return;
} }
// Dead // Dead
else else

@ -115,7 +115,7 @@ NLMISC::CRGBA CEntityCL::_UserPackAnimalColor;
NLMISC::CRGBA CEntityCL::_PvpEnemyColor; NLMISC::CRGBA CEntityCL::_PvpEnemyColor;
NLMISC::CRGBA CEntityCL::_PvpNeutralColor; NLMISC::CRGBA CEntityCL::_PvpNeutralColor;
NLMISC::CRGBA CEntityCL::_PvpAllyInTeamColor; NLMISC::CRGBA CEntityCL::_PvpAllyInTeamColor;
NLMISC::CRGBA CEntityCL::_PvpAllyInGuildColor; NLMISC::CRGBA CEntityCL::_PvpAllyInLeagueColor;
NLMISC::CRGBA CEntityCL::_PvpAllyColor; NLMISC::CRGBA CEntityCL::_PvpAllyColor;
NLMISC::CRGBA CEntityCL::_GMTitleColor[CHARACTER_TITLE::EndGmTitle - CHARACTER_TITLE::BeginGmTitle + 1]; NLMISC::CRGBA CEntityCL::_GMTitleColor[CHARACTER_TITLE::EndGmTitle - CHARACTER_TITLE::BeginGmTitle + 1];
uint8 CEntityCL::_InvalidGMTitleCode = 0xFF; uint8 CEntityCL::_InvalidGMTitleCode = 0xFF;
@ -2295,6 +2295,7 @@ void CEntityCL::onStringAvailable(uint /* stringId */, const ucstring &value)
womenTitle = true; womenTitle = true;
} }
const ucstring replacement(STRING_MANAGER::CStringManagerClient::getTitleLocalizedName(_TitleRaw,womenTitle)); const ucstring replacement(STRING_MANAGER::CStringManagerClient::getTitleLocalizedName(_TitleRaw,womenTitle));
_Tags = STRING_MANAGER::CStringManagerClient::getTitleInfos(_TitleRaw,womenTitle);
if (!replacement.empty() || !ClientCfg.DebugStringManager) if (!replacement.empty() || !ClientCfg.DebugStringManager)
{ {
// build the final name // build the final name
@ -2436,7 +2437,6 @@ public:
CEntityCL::_PvpEnemyColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPENEMY")->getValueRGBA(); CEntityCL::_PvpEnemyColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPENEMY")->getValueRGBA();
CEntityCL::_PvpAllyColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPALLY")->getValueRGBA(); CEntityCL::_PvpAllyColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPALLY")->getValueRGBA();
CEntityCL::_PvpAllyInTeamColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPALLYINTEAM")->getValueRGBA(); CEntityCL::_PvpAllyInTeamColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPALLYINTEAM")->getValueRGBA();
CEntityCL::_PvpAllyInGuildColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPALLYINGUILD")->getValueRGBA();
CEntityCL::_PvpNeutralColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPNEUTRAL")->getValueRGBA(); CEntityCL::_PvpNeutralColor = pIM->getDbProp("UI:SAVE:ENTITY:COLORS:PVPNEUTRAL")->getValueRGBA();
// don't save these colors in .icfg because players can't change them // don't save these colors in .icfg because players can't change them
@ -2463,7 +2463,7 @@ bool CEntityCL::isTarget () const
//----------------------------------------------- //-----------------------------------------------
bool CEntityCL::isInGuild () const bool CEntityCL::isInSameGuild () const
{ {
if (Type != Player && Type != User) if (Type != Player && Type != User)
return false; return false;
@ -2477,6 +2477,33 @@ bool CEntityCL::isInGuild () const
//----------------------------------------------- //-----------------------------------------------
bool CEntityCL::oneInLeague () const
{
if (Type != Player && Type != User)
return false;
const uint32 leagueID = getLeagueID();
if ((UserEntity && (UserEntity->getLeagueID() != 0)) || leagueID != 0)
return true;
return false;
}
//-----------------------------------------------
bool CEntityCL::isInSameLeague () const
{
if (Type != Player && Type != User)
return false;
const uint32 leagueID = getLeagueID();
if ((leagueID != 0) && UserEntity && (leagueID == UserEntity->getLeagueID()))
return true;
return false;
}
//-----------------------------------------------
NLMISC::CRGBA CEntityCL::getColor () const NLMISC::CRGBA CEntityCL::getColor () const
{ {
// target // target
@ -2511,46 +2538,43 @@ NLMISC::CRGBA CEntityCL::getColor () const
{ {
if (isEnemy()) if (isEnemy())
{ {
if (getPvpMode()&PVP_MODE::PvpFactionFlagged || getPvpMode()&PVP_MODE::PvpChallenge) if (getPvpMode()&PVP_MODE::PvpFaction)
return _PvpEnemyColor; return CRGBA::CRGBA(min(255, _PvpEnemyColor.R+150), min(255, _PvpEnemyColor.G+150), min(255, _PvpEnemyColor.B+150),_PvpEnemyColor.A);
else else
return CRGBA(min(255, _PvpEnemyColor.R+150), min(255, _PvpEnemyColor.G+150), min(255, _PvpEnemyColor.B+150),_PvpEnemyColor.A); return _PvpEnemyColor;
} }
} }
// neutral pvp
if (isNeutralPVP())
{
if (isInTeam())
return _PvpAllyInTeamColor;
if (isInGuild())
return _PvpAllyInGuildColor;
return _PvpNeutralColor;
}
// ally // ally
if (isAlly()) if (isAlly())
{ {
if (getPvpMode() & PVP_MODE::PvpFactionFlagged) if (getPvpMode() & PVP_MODE::PvpFactionFlagged)
{ {
if (isInTeam()) if(isInSameLeague())
return _PvpAllyInTeamColor; return CRGBA::CRGBA(max(0, _PvpAllyColor.R-100), max(0, _PvpAllyColor.G-100), max(0, _PvpAllyColor.B-100),_PvpAllyColor.A);
if(isInGuild()) return CRGBA::CRGBA(max(0, _PvpAllyInTeamColor.R-100), max(0, _PvpAllyInTeamColor.G-100), max(0, _PvpAllyInTeamColor.B-100),_PvpAllyInTeamColor.A);
return _PvpAllyInGuildColor;
return _PvpAllyColor;
} }
else else
{ {
if (isInTeam()) if(isInSameLeague())
return CRGBA(min(255, _PvpAllyInTeamColor.R+150), min(255, _PvpAllyInTeamColor.G+150), min(255, _PvpAllyInTeamColor.B+150),_PvpAllyInTeamColor.A); return _PvpAllyColor;
if(isInGuild()) return _PvpAllyInTeamColor;
return CRGBA(min(255, _PvpAllyInGuildColor.R+150), min(255, _PvpAllyInGuildColor.G+150), min(255, _PvpAllyInGuildColor.B+150),_PvpAllyInGuildColor.A);
return CRGBA(min(255, _PvpAllyColor.R+150), min(255, _PvpAllyColor.G+150), min(255, _PvpAllyColor.B+150),_PvpAllyColor.A);
} }
} }
// neutral pvp
if (isNeutralPVP())
return _PvpNeutralColor;
// neutral // neutral
if (isInTeam()) if (isInTeam())
return _GroupColor; return _GroupColor;
if (isInGuild())
// neutral
if (isInSameLeague())
return CRGBA::CRGBA(min(255, _GroupColor.R+50), min(255, _GroupColor.G+50), min(255, _GroupColor.B+50),_GroupColor.A);
if (isInSameGuild())
return _GuildColor; return _GuildColor;
} }
return _EntitiesColor[Type]; return _EntitiesColor[Type];

@ -686,7 +686,7 @@ public:
virtual bool isNeutralPVP() const { return false; } virtual bool isNeutralPVP() const { return false; }
/// Return true if this player has the viewing properties of a friend (inscene bars...) /// Return true if this player has the viewing properties of a friend (inscene bars...)
virtual bool isViewedAsFriend() const { return isNeutral() || isFriend() || isInTeam() || isInGuild(); } virtual bool isViewedAsFriend() const { return isNeutral() || isFriend() || isInTeam() || isInSameGuild() || isInSameLeague(); }
/// Return the People for the entity (unknown by default) /// Return the People for the entity (unknown by default)
virtual EGSPD::CPeople::TPeople people() const; virtual EGSPD::CPeople::TPeople people() const;
@ -733,7 +733,13 @@ public:
bool isInTeam () const { return _IsInTeam; } bool isInTeam () const { return _IsInTeam; }
// Return true if this entity is in the user guild // Return true if this entity is in the user guild
bool isInGuild () const; bool isInSameGuild () const;
// Return true if this entity is in the user league
bool isInSameLeague () const;
// Return true if this entity or the user is in a league
bool oneInLeague () const;
// Return true if this entity is a Mount owned by the User // Return true if this entity is a Mount owned by the User
bool isUserMount () const {return _IsUserMount;} bool isUserMount () const {return _IsUserMount;}
@ -746,8 +752,9 @@ public:
virtual uint64 getGuildSymbol () const { return 0; } virtual uint64 getGuildSymbol () const { return 0; }
virtual uint32 getEventFactionID() const { return 0; } virtual uint32 getEventFactionID() const { return 0; }
virtual uint8 getPvpMode() const { return PVP_MODE::None; } virtual uint16 getPvpMode() const { return PVP_MODE::None; }
virtual PVP_CLAN::TPVPClan getPvpClan() const { return PVP_CLAN::None; } virtual PVP_CLAN::TPVPClan getPvpClan() const { return PVP_CLAN::None; }
virtual uint32 getLeagueID() const { return 0; }
virtual uint16 getOutpostId() const { return 0; } virtual uint16 getOutpostId() const { return 0; }
virtual OUTPOSTENUMS::TPVPSide getOutpostSide() const { return OUTPOSTENUMS::UnknownPVPSide; } virtual OUTPOSTENUMS::TPVPSide getOutpostSide() const { return OUTPOSTENUMS::UnknownPVPSide; }
@ -760,6 +767,16 @@ public:
return _Title; return _Title;
} }
/// Return the entity tags
const ucstring &getTag(uint8 id) const
{
if (_Tags.size() > id) {
return _Tags[id];
}
static ucstring empty;
return empty;
}
/// Return the raw unparsed entity title /// Return the raw unparsed entity title
const ucstring getTitleRaw() const const ucstring getTitleRaw() const
{ {
@ -910,6 +927,8 @@ protected:
ucstring _EntityName; ucstring _EntityName;
// Current entity title // Current entity title
ucstring _Title; ucstring _Title;
// Current entity tags
std::vector<ucstring> _Tags;
// Current entity title string id // Current entity title string id
std::string _TitleRaw; std::string _TitleRaw;
// Current permanent content symbol for the entity // Current permanent content symbol for the entity
@ -1006,7 +1025,7 @@ protected:
static NLMISC::CRGBA _PvpEnemyColor; static NLMISC::CRGBA _PvpEnemyColor;
static NLMISC::CRGBA _PvpNeutralColor; static NLMISC::CRGBA _PvpNeutralColor;
static NLMISC::CRGBA _PvpAllyInTeamColor; static NLMISC::CRGBA _PvpAllyInTeamColor;
static NLMISC::CRGBA _PvpAllyInGuildColor; static NLMISC::CRGBA _PvpAllyInLeagueColor;
static NLMISC::CRGBA _PvpAllyColor; static NLMISC::CRGBA _PvpAllyColor;
// colors for GM players // colors for GM players
static NLMISC::CRGBA _GMTitleColor[CHARACTER_TITLE::EndGmTitle - CHARACTER_TITLE::BeginGmTitle + 1]; static NLMISC::CRGBA _GMTitleColor[CHARACTER_TITLE::EndGmTitle - CHARACTER_TITLE::BeginGmTitle + 1];

@ -57,6 +57,9 @@
#include "sbrick_manager.h" #include "sbrick_manager.h"
#include "sphrase_manager.h" #include "sphrase_manager.h"
#include "action_handler_help.h" #include "action_handler_help.h"
#include "nel/misc/i18n.h"
#include "nel/misc/algo.h"
#include "nel/net/email.h"
#include "game_share/mission_desc.h" #include "game_share/mission_desc.h"
#include "game_share/inventories.h" #include "game_share/inventories.h"
#include "game_share/visual_slot_manager.h" #include "game_share/visual_slot_manager.h"
@ -378,7 +381,7 @@ CInterfaceGroup *CInterfaceHelp::activateNextWindow(CDBCtrlSheet *elt, sint forc
setup.setupDefaultIDs(); setup.setupDefaultIDs();
setup.SrcSheet = elt; setup.SrcSheet = elt;
setup.HelpWindow = group; setup.HelpWindow = group;
setupCreatorName(setup); //setupCreatorName(setup);
// Hide elements by defaults // Hide elements by defaults
resetSheetHelp(setup); resetSheetHelp(setup);
@ -2064,6 +2067,12 @@ void getItemText (CDBCtrlSheet *item, ucstring &itemText, const CItemSheet*pIS)
strFindReplace(itemText, "%r2_comment_text", toString(itemInfo.R2ItemComment)); strFindReplace(itemText, "%r2_comment_text", toString(itemInfo.R2ItemComment));
} }
break; break;
case ITEMFAMILY::PET_ANIMAL_TICKET:
{
string nr = (itemInfo.PetNumber > 0) ? toString(itemInfo.PetNumber) : "(slot)" + toString(item->getIndexInDB());
strFindReplace(itemText, "%petnumber", nr);
}
break;
default: default:
{ {
strFindReplace(itemText, "%no_rent", pIS->IsItemNoRent ? CI18N::get("uihelpItemNoRent") : string("")); strFindReplace(itemText, "%no_rent", pIS->IsItemNoRent ? CI18N::get("uihelpItemNoRent") : string(""));
@ -2745,8 +2754,15 @@ void setupCreatorName(CSheetHelpSetup &setup)
CViewText *vthd = dynamic_cast<CViewText*>(setup.HelpWindow->getView("creator_header")); CViewText *vthd = dynamic_cast<CViewText*>(setup.HelpWindow->getView("creator_header"));
if (vtid != NULL) if (vtid != NULL)
{ {
// if not an item, disable the view bool bIsRM = false;
if(!setup.SrcSheet || setup.SrcSheet->getType()!=CCtrlSheetInfo::SheetType_Item ) if (setup.SrcSheet)
{
const CItemSheet *pIS= dynamic_cast<const CItemSheet*>(SheetMngr.get(CSheetId(setup.SrcSheet->getSheetId())));
bIsRM = (pIS && pIS->Family == ITEMFAMILY::RAW_MATERIAL);
}
// if a RM or not an item, disable the view
if(!setup.SrcSheet || bIsRM || setup.SrcSheet->getType()!=CCtrlSheetInfo::SheetType_Item )
{ {
// important else a brick could display a creator name.... // important else a brick could display a creator name....
vtid->setActive(false); vtid->setActive(false);
@ -3569,6 +3585,31 @@ public:
}; };
REGISTER_ACTION_HANDLER( CHandlerAuraModifierTooltip, "aura_modifier_tooltip"); REGISTER_ACTION_HANDLER( CHandlerAuraModifierTooltip, "aura_modifier_tooltip");
// ***************************************************************************
class CHandlerUserPaToolTip : public IActionHandler
{
public:
virtual void execute(CCtrlBase *pCaller, const string &Params)
{
CInterfaceManager *pIM= CInterfaceManager::getInstance();
uint8 index;
fromString(Params, index);
--index; // Param is 1-based so subtract 1
if (index < 0 || index >= MAX_INVENTORY_ANIMAL)
{
return;
}
ucstring txt;
CCDBNodeLeaf *node = pIM->getDbProp(toString("SERVER:PACK_ANIMAL:BEAST%d:NAME", index));
if (node && CStringManagerClient::instance()->getDynString(node->getValue32(), txt))
{
pIM->setContextHelpText(CEntityCL::removeTitleFromName(txt));
}
}
};
REGISTER_ACTION_HANDLER( CHandlerUserPaToolTip, "userpa_name_tooltip");
// *************************************************************************** // ***************************************************************************
class CHandlerAnimalDeadPopupTooltip : public IActionHandler class CHandlerAnimalDeadPopupTooltip : public IActionHandler
@ -3922,7 +3963,7 @@ public:
#ifdef NL_OS_WINDOWS #ifdef NL_OS_WINDOWS
if (Driver) if (Driver)
{ {
HWND wnd = Driver->getDisplay(); HWND wnd = (HWND) Driver->getDisplay();
ShowWindow(wnd, SW_MINIMIZE); ShowWindow(wnd, SW_MINIMIZE);
} }
#endif #endif

@ -64,6 +64,15 @@ void refreshItemHelp(CSheetHelpSetup &setup);
// refresh help for a mission // refresh help for a mission
void refreshMissionHelp(CSheetHelpSetup &setup, const CPrerequisitInfos &infos); void refreshMissionHelp(CSheetHelpSetup &setup, const CPrerequisitInfos &infos);
class CPetAnimalItemInfoWaiter : public IItemInfoWaiter
{
void infoReceived()
{
//ItemSheet
//ItemSlotId
CClientItemInfo info = getInventory().getItemInfo(ItemSlotId);
}
};
// *************************************************************************** // ***************************************************************************

@ -31,9 +31,11 @@
#include "../net_manager.h" #include "../net_manager.h"
#include "group_menu.h" #include "group_menu.h"
#include "../global.h" #include "../global.h"
#include "group_html.h"
// //
#include "game_share/inventories.h" #include "game_share/inventories.h"
#include "game_share/bot_chat_types.h"
#include "macrocmd_manager.h" #include "macrocmd_manager.h"
#include "inventory_manager.h" #include "inventory_manager.h"
@ -43,6 +45,7 @@
#include "view_bitmap.h" #include "view_bitmap.h"
extern CSheetManager SheetMngr; extern CSheetManager SheetMngr;
extern NLMISC::CLog g_log;
using namespace std; using namespace std;
using namespace NLMISC; using namespace NLMISC;
@ -80,8 +83,6 @@ void CInterfaceItemEdition::setCurrWindow(CDBCtrlSheet* ctrlSheet, const std::st
_CurrWindow.IsInEditionMode = isInEditionMode; _CurrWindow.IsInEditionMode = isInEditionMode;
_CurrWindow.begin(); _CurrWindow.begin();
} }
} }
// ******************************************************************************************** // ********************************************************************************************
@ -153,13 +154,26 @@ void CInterfaceItemEdition::CItemEditionWindow::infoReceived()
if (itemInfo.CustomText.empty()) if (itemInfo.CustomText.empty())
display->setTextFormatTaged(ucstring(STRING_MANAGER::CStringManagerClient::getItemLocalizedDescription(pIS->Id))); display->setTextFormatTaged(ucstring(STRING_MANAGER::CStringManagerClient::getItemLocalizedDescription(pIS->Id)));
else else
display->setTextFormatTaged(itemInfo.CustomText); {
ucstring text = itemInfo.CustomText;
string::size_type delimiter = text.find(' ');
if(text.size() > 3 && text[0]=='@' && text[1]=='W' && text[2]=='E' && text[3]=='B')
{
CGroupHTML *pGH = dynamic_cast<CGroupHTML*>(pIM->getElementFromId("ui:interface:web_transactions:content:html"));
if (pGH)
pGH->browse(ucstring(text.substr(4, delimiter-4)).toString().c_str());
if (delimiter == string::npos)
group->setActive(false);
else
text = text.substr(delimiter, text.size()-delimiter);
} }
display->setTextFormatTaged(text);
}
}
} }
} }
} }
} }
@ -278,7 +292,21 @@ void CInterfaceItemEdition::CItemEditionWindow::begin()
if (itemInfo.CustomText.empty()) if (itemInfo.CustomText.empty())
display->setTextFormatTaged(ucstring(STRING_MANAGER::CStringManagerClient::getItemLocalizedDescription(pIS->Id))); display->setTextFormatTaged(ucstring(STRING_MANAGER::CStringManagerClient::getItemLocalizedDescription(pIS->Id)));
else else
display->setTextFormatTaged(itemInfo.CustomText); {
ucstring text = itemInfo.CustomText;
string::size_type delimiter = text.find(' ');
if(text.size() > 3 && text[0]=='@' && text[1]=='W' && text[2]=='E' && text[3]=='B')
{
CGroupHTML *pGH = dynamic_cast<CGroupHTML*>(pIM->getElementFromId("ui:interface:web_transactions:content:html"));
if (pGH)
pGH->browse(ucstring(text.substr(4, delimiter-4)).toString().c_str());
if (delimiter == string::npos)
group->setActive(false);
else
text = text.substr(delimiter, text.size()-delimiter);
}
display->setTextFormatTaged(text);
}
} }
else else
{ {
@ -287,7 +315,6 @@ void CInterfaceItemEdition::CItemEditionWindow::begin()
} }
} }
} }
} }
} }
} }
@ -366,7 +393,6 @@ void CInterfaceItemEdition::CItemEditionWindow::validate()
text = editBoxLarge->getInputString(); text = editBoxLarge->getInputString();
} }
if (textValid) if (textValid)
{ {
CBitMemStream out; CBitMemStream out;
@ -972,6 +998,12 @@ bool checkCanExchangeItem(CDBCtrlSheet *pCSSrc)
bDropOrSell = pIS->canExchangeOrGive(PlayerTrade.BotChatGiftContext); bDropOrSell = pIS->canExchangeOrGive(PlayerTrade.BotChatGiftContext);
} }
// Locked by owner; cannot trade
if (pCSSrc->getLockedByOwner())
{
return false;
}
// Special case if this is an animal ticket // Special case if this is an animal ticket
if ((pIS != NULL) && (pIS->Family == ITEMFAMILY::PET_ANIMAL_TICKET)) if ((pIS != NULL) && (pIS->Family == ITEMFAMILY::PET_ANIMAL_TICKET))
{ {
@ -1209,6 +1241,13 @@ class CHandlerDestroyItem : public IActionHandler
nlwarning("<CHandlerDestroyItem::execute> no caller sheet found"); nlwarning("<CHandlerDestroyItem::execute> no caller sheet found");
return; return;
} }
// Don't destroy locked items
if (item->getLockedByOwner())
{
return;
}
// if the item is currently selected, removes the selection // if the item is currently selected, removes the selection
if (item == CDBCtrlSheet::getCurrSelection()) if (item == CDBCtrlSheet::getCurrSelection())
{ {
@ -1712,11 +1751,15 @@ class CHandlerItemMenuCheck : public IActionHandler
CViewTextMenu *pXpCatalyserUse = dynamic_cast<CViewTextMenu*>(pMenu->getView("xp_catalyser_use")); CViewTextMenu *pXpCatalyserUse = dynamic_cast<CViewTextMenu*>(pMenu->getView("xp_catalyser_use"));
CViewTextMenu *pDrop = dynamic_cast<CViewTextMenu*>(pMenu->getView("drop")); CViewTextMenu *pDrop = dynamic_cast<CViewTextMenu*>(pMenu->getView("drop"));
CViewTextMenu *pDestroy = dynamic_cast<CViewTextMenu*>(pMenu->getView("destroy")); CViewTextMenu *pDestroy = dynamic_cast<CViewTextMenu*>(pMenu->getView("destroy"));
CViewTextMenu *pLockUnlock = dynamic_cast<CViewTextMenu*>(pMenu->getView("lockunlock"));
CViewTextMenu *pMoveSubMenu = dynamic_cast<CViewTextMenu*>(pMenu->getView("move")); CViewTextMenu *pMoveSubMenu = dynamic_cast<CViewTextMenu*>(pMenu->getView("move"));
CViewTextMenu *pMoveToBag = dynamic_cast<CViewTextMenu*>(pMenu->getView("bag")); CViewTextMenu *pMoveToBag = dynamic_cast<CViewTextMenu*>(pMenu->getView("bag"));
CViewTextMenu *pMoveToGuild = dynamic_cast<CViewTextMenu*>(pMenu->getView("guild")); CViewTextMenu *pMoveToGuild = dynamic_cast<CViewTextMenu*>(pMenu->getView("guild"));
CViewTextMenu *pMoveToRoom = dynamic_cast<CViewTextMenu*>(pMenu->getView("room")); CViewTextMenu *pMoveToRoom = dynamic_cast<CViewTextMenu*>(pMenu->getView("room"));
CViewTextMenu *pMoveToPa[MAX_INVENTORY_ANIMAL]; CViewTextMenu *pMoveToPa[MAX_INVENTORY_ANIMAL];
bool bIsLockedByOwner = pCS->getLockedByOwner();
for(i=0;i<MAX_INVENTORY_ANIMAL;i++) for(i=0;i<MAX_INVENTORY_ANIMAL;i++)
{ {
pMoveToPa[i]= dynamic_cast<CViewTextMenu*>(pMenu->getView(toString("pa%d", i))); pMoveToPa[i]= dynamic_cast<CViewTextMenu*>(pMenu->getView(toString("pa%d", i)));
@ -1735,24 +1778,27 @@ class CHandlerItemMenuCheck : public IActionHandler
if(pXpCatalyserUse) pXpCatalyserUse->setActive(false); if(pXpCatalyserUse) pXpCatalyserUse->setActive(false);
if(pItemTextDisplay) pItemTextDisplay->setActive(false); if(pItemTextDisplay) pItemTextDisplay->setActive(false);
if(pItemTextEdition) pItemTextEdition->setActive(false); if(pItemTextEdition) pItemTextEdition->setActive(false);
if(pLockUnlock) pLockUnlock->setActive(true);
const CItemSheet *pIS = pCS->asItemSheet(); const CItemSheet *pIS = pCS->asItemSheet();
if (invId != INVENTORIES::guild) if (invId != INVENTORIES::guild)
if (pIS != NULL) if (pIS != NULL)
{ {
if (pCrisEnchant && pIS->Family == ITEMFAMILY::CRYSTALLIZED_SPELL) if (pCrisEnchant && pIS->Family == ITEMFAMILY::CRYSTALLIZED_SPELL && !bIsLockedByOwner)
pCrisEnchant->setActive(true); pCrisEnchant->setActive(true);
if (pCrisReload && pIS->Family == ITEMFAMILY::ITEM_SAP_RECHARGE) if (pCrisReload && pIS->Family == ITEMFAMILY::ITEM_SAP_RECHARGE && !bIsLockedByOwner)
pCrisReload->setActive(true); pCrisReload->setActive(true);
// teleport can be used only from bag (NB: should not exist in mektoub....) // teleport can be used only from bag (NB: should not exist in mektoub....)
if (pTeleportUse && pIS->Family == ITEMFAMILY::TELEPORT && pCS->getInventoryIndex()==INVENTORIES::bag) if (pTeleportUse && pIS->Family == ITEMFAMILY::TELEPORT && pCS->getInventoryIndex()==INVENTORIES::bag && !bIsLockedByOwner)
{ {
pTeleportUse->setActive(true); pTeleportUse->setActive(true);
} }
if (pItemConsume && pIS->IsConsumable == true && pCS->getInventoryIndex()==INVENTORIES::bag) if (pItemConsume && pIS->IsConsumable == true && pCS->getInventoryIndex()==INVENTORIES::bag && !bIsLockedByOwner)
{ {
pItemConsume->setActive(true); pItemConsume->setActive(true);
} }
if (pXpCatalyserUse && pIS->Family == ITEMFAMILY::XP_CATALYSER && pCS->getInventoryIndex()==INVENTORIES::bag) if (pXpCatalyserUse && pIS->Family == ITEMFAMILY::XP_CATALYSER && pCS->getInventoryIndex()==INVENTORIES::bag && !bIsLockedByOwner)
{ {
pXpCatalyserUse->setActive(true); pXpCatalyserUse->setActive(true);
} }
@ -1815,9 +1861,10 @@ class CHandlerItemMenuCheck : public IActionHandler
for(i=0;i<MAX_INVENTORY_ANIMAL;i++) for(i=0;i<MAX_INVENTORY_ANIMAL;i++)
if(pMoveToPa[i]) pMoveToPa[i]->setActive(false); if(pMoveToPa[i]) pMoveToPa[i]->setActive(false);
// additionnaly, cannot drop/destroy an animal item. // additionnaly, cannot drop/destroy/lock an animal item.
if(pDrop) pDrop->setActive(false); if(pDrop) pDrop->setActive(false);
if(pDestroy) pDestroy->setActive(false); if(pDestroy) pDestroy->setActive(false);
if(pLockUnlock) pLockUnlock->setActive(false);
} }
else else
{ {
@ -1845,6 +1892,7 @@ class CHandlerItemMenuCheck : public IActionHandler
// std case: can drop / destroy // std case: can drop / destroy
if(pDrop) pDrop->setActive(invId!=INVENTORIES::guild); if(pDrop) pDrop->setActive(invId!=INVENTORIES::guild);
if(pDestroy) pDestroy->setActive(invId!=INVENTORIES::guild); if(pDestroy) pDestroy->setActive(invId!=INVENTORIES::guild);
if(pLockUnlock) pLockUnlock->setActive(invId!=INVENTORIES::guild);
} }
// hide the move entry completely? // hide the move entry completely?
@ -1899,6 +1947,29 @@ class CHandlerItemMenuCheck : public IActionHandler
pItemTextDisplay->setGrayed(pIM->getDbProp("UI:VARIABLES:ISACTIVE:PHRASE_EDIT_CUSTOM")->getValueBool()); pItemTextDisplay->setGrayed(pIM->getDbProp("UI:VARIABLES:ISACTIVE:PHRASE_EDIT_CUSTOM")->getValueBool());
} }
if (pCS->getGrayed())
{
if (pEquip) pEquip->setActive(false);
if (pDestroy) pDestroy->setActive(false);
if (pLockUnlock) pLockUnlock->setActive(false);
if (pMoveSubMenu) pMoveSubMenu->setActive(false);
}
if (bIsLockedByOwner)
{
if (pLockUnlock) pLockUnlock->setHardText("uimUnlockItem");
// Cannot drop/destroy if locked by owner
if (pDrop) pDrop->setActive(false);
if (pDestroy) pDestroy->setActive(false);
}
else
{
if (pLockUnlock) pLockUnlock->setHardText("uimLockItem");
}
// Only show lock menu item if inventory contains the info
if (pLockUnlock) pLockUnlock->setActive(pCS->canOwnerLock());
// **** Gray Entries // **** Gray Entries
// If ourselves are not available, then gray all // If ourselves are not available, then gray all
@ -1911,6 +1982,7 @@ class CHandlerItemMenuCheck : public IActionHandler
if(pXpCatalyserUse) pXpCatalyserUse->setGrayed(true); if(pXpCatalyserUse) pXpCatalyserUse->setGrayed(true);
if(pDrop) pDrop->setGrayed(true); if(pDrop) pDrop->setGrayed(true);
if(pDestroy) pDestroy->setGrayed(true); if(pDestroy) pDestroy->setGrayed(true);
if(pLockUnlock) pLockUnlock->setGrayed(true);
if(pMoveSubMenu) pMoveSubMenu->setGrayed(true); if(pMoveSubMenu) pMoveSubMenu->setGrayed(true);
if(pMoveToBag) pMoveToBag->setGrayed(true); if(pMoveToBag) pMoveToBag->setGrayed(true);
for(i=0;i<MAX_INVENTORY_ANIMAL;i++) for(i=0;i<MAX_INVENTORY_ANIMAL;i++)
@ -1929,6 +2001,7 @@ class CHandlerItemMenuCheck : public IActionHandler
if(pXpCatalyserUse) pXpCatalyserUse->setGrayed(false); if(pXpCatalyserUse) pXpCatalyserUse->setGrayed(false);
if(pDrop) pDrop->setGrayed(false); if(pDrop) pDrop->setGrayed(false);
if(pDestroy) pDestroy->setGrayed(false); if(pDestroy) pDestroy->setGrayed(false);
if(pLockUnlock) pLockUnlock->setGrayed(false);
if(pMoveSubMenu) pMoveSubMenu->setGrayed(false); if(pMoveSubMenu) pMoveSubMenu->setGrayed(false);
// check each inventory dest if available // check each inventory dest if available
@ -1956,6 +2029,45 @@ class CHandlerItemMenuDeactivate : public IActionHandler
}; };
REGISTER_ACTION_HANDLER( CHandlerItemMenuDeactivate, "item_menu_deactivate" ); REGISTER_ACTION_HANDLER( CHandlerItemMenuDeactivate, "item_menu_deactivate" );
// ***************************************************************************
class CHandlerItemMenuBaseCheck : public IActionHandler
{
void execute (CCtrlBase *pCaller, const std::string &/* sParams */)
{
CInterfaceManager *pIM = CInterfaceManager::getInstance();
// Get the ctrl sheet that launched this menu
CDBCtrlSheet *pCS = dynamic_cast<CDBCtrlSheet*>(pIM->getCtrlLaunchingModal());
if (pCS == NULL) return;
INVENTORIES::TInventory invId= (INVENTORIES::TInventory)pCS->getInventoryIndex();
// Get the menu launched
CInterfaceGroup *pMenu= dynamic_cast<CInterfaceGroup*>(pCaller);
if(!pMenu) return;
// Get all needed text entries
CViewTextMenu *pDestroy = dynamic_cast<CViewTextMenu*>(pMenu->getView("destroy"));
CViewTextMenu *pLockUnlock = dynamic_cast<CViewTextMenu*>(pMenu->getView("lockunlock"));
if (pCS->getLockedByOwner())
{
pLockUnlock->setHardText("uimUnlockItem");
// Cannot destroy if locked by owner
if (pDestroy) pDestroy->setActive(false);
}
else
{
pLockUnlock->setHardText("uimLockItem");
if (pDestroy) pDestroy->setActive(true);
}
}
};
REGISTER_ACTION_HANDLER( CHandlerItemMenuBaseCheck, "item_menu_base_check" );
// *************************************************************************** // ***************************************************************************
static void sendMsgUseItem(uint16 slot) static void sendMsgUseItem(uint16 slot)
{ {

@ -33,7 +33,7 @@
#include "group_editbox.h" #include "group_editbox.h"
#include "dbview_bar.h" #include "dbview_bar.h"
#include "skill_manager.h" #include "skill_manager.h"
#include "game_share/bot_chat_types.h"
using namespace std; using namespace std;
using namespace NLMISC; using namespace NLMISC;
@ -69,7 +69,9 @@ const std::string FaberPhraseItemResultGroup= FaberPhraseWindow + ":header_opene
// *************************************************************************** // ***************************************************************************
CActionPhraseFaber::CActionPhraseFaber() CActionPhraseFaber::CActionPhraseFaber()
{ {
_InventoryMirror.resize(INVENTORIES::NUM_INVENTORY * MAX_PLAYER_INV_ENTRIES); uint size = MAX_PLAYER_INV_ENTRIES + (MAX_ANIMALINV_ENTRIES * MAX_INVENTORY_ANIMAL) +
MAX_GUILDINV_ENTRIES + MAX_ROOMINV_ENTRIES;
_InventoryMirror.resize(size);
_InventoryObsSetup= false; _InventoryObsSetup= false;
_ExecuteFromItemPlanBrick= NULL; _ExecuteFromItemPlanBrick= NULL;
} }
@ -275,25 +277,64 @@ void CActionPhraseFaber::fillFaberPlanSelection(const std::string &brickDB, ui
} }
// *************************************************************************** // ***************************************************************************
CItemImage *CActionPhraseFaber::getInvMirrorItemImage(uint slotIndex) CItemImage *CActionPhraseFaber::getInvMirrorItemImage(uint slotIndex, uint& invId, uint& indexInInv)
{ {
uint invId= slotIndex/MAX_PLAYER_INV_ENTRIES; if (slotIndex < MAX_PLAYER_INV_ENTRIES)
uint indexInInv= slotIndex%MAX_PLAYER_INV_ENTRIES; {
invId = INVENTORIES::bag;
indexInInv = slotIndex;
return &getInventory().getBagItem(slotIndex);
}
slotIndex -= MAX_PLAYER_INV_ENTRIES;
if (slotIndex < (MAX_ANIMALINV_ENTRIES * MAX_INVENTORY_ANIMAL))
{
uint animal = slotIndex / MAX_ANIMALINV_ENTRIES;
uint index = slotIndex % MAX_ANIMALINV_ENTRIES;
invId = INVENTORIES::pet_animal + animal;
indexInInv = index;
return &getInventory().getPAItem(animal, index);
}
slotIndex -= (MAX_ANIMALINV_ENTRIES * MAX_INVENTORY_ANIMAL);
if (slotIndex < MAX_GUILDINV_ENTRIES)
{
if (getInventory().isInventoryAvailable(INVENTORIES::guild))
{
CInterfaceManager *im = CInterfaceManager::getInstance();
CCDBNodeBranch *itemBranch = im->getDbBranch(SERVER_INVENTORY ":GUILD:" + toString(slotIndex));
static CItemImage image;
image.build(itemBranch);
invId = INVENTORIES::guild;
indexInInv = slotIndex;
return &image;
}
return NULL;
}
slotIndex -= MAX_GUILDINV_ENTRIES;
// get the item image from bag, steed, pack animal... if (slotIndex < MAX_ROOMINV_ENTRIES)
if(invId==INVENTORIES::bag && indexInInv<MAX_BAGINV_ENTRIES) {
return &getInventory().getBagItem(indexInInv); if (getInventory().isInventoryAvailable(INVENTORIES::player_room))
else if(invId>=INVENTORIES::pet_animal && invId<INVENTORIES::pet_animal+MAX_INVENTORY_ANIMAL && indexInInv<MAX_ANIMALINV_ENTRIES) {
return &getInventory().getPAItem(invId-INVENTORIES::pet_animal, indexInInv); CInterfaceManager *im = CInterfaceManager::getInstance();
CCDBNodeBranch *itemBranch = im->getDbBranch(SERVER_INVENTORY ":ROOM:" + toString(slotIndex));
static CItemImage image;
image.build(itemBranch);
invId = INVENTORIES::player_room;
indexInInv = slotIndex;
return &image;
}
return NULL;
}
return NULL; return NULL;
} }
// *************************************************************************** // ***************************************************************************
bool CActionPhraseFaber::isMpAvailable(CItemSheet *mpSheet, uint slotIndex) const bool CActionPhraseFaber::isMpAvailable(CItemSheet *mpSheet, uint invId, uint slotIndex) const
{ {
uint invId= slotIndex / MAX_PLAYER_INV_ENTRIES;
return mpSheet && mpSheet->Family==ITEMFAMILY::RAW_MATERIAL && getInventory().isInventoryAvailable((INVENTORIES::TInventory)invId); return mpSheet && mpSheet->Family==ITEMFAMILY::RAW_MATERIAL && getInventory().isInventoryAvailable((INVENTORIES::TInventory)invId);
} }
@ -396,14 +437,14 @@ void CActionPhraseFaber::validateFaberPlanSelection(CSBrickSheet *itemPlanBrick
_InventoryMirror[i].reset(); _InventoryMirror[i].reset();
} }
uint invId = 0;
uint indexInInv = 0;
// Run all the inventories. // Run all the inventories.
for(i=0;i<_InventoryMirror.size();i++) for(i=0;i<_InventoryMirror.size();i++)
{ {
uint invId= i/MAX_PLAYER_INV_ENTRIES; CItemImage *itemImage= getInvMirrorItemImage(i, invId, indexInInv);
uint indexInInv= i%MAX_PLAYER_INV_ENTRIES; bool bLockedByOwner = itemImage && itemImage->getLockedByOwner();
CItemImage *itemImage= getInvMirrorItemImage(i); // item found and not locked?
// item found?
if(itemImage) if(itemImage)
{ {
// setup the origin // setup the origin
@ -413,7 +454,7 @@ void CActionPhraseFaber::validateFaberPlanSelection(CSBrickSheet *itemPlanBrick
// The item must be a mp // The item must be a mp
CSheetId sheetId= CSheetId(itemImage->getSheetID()); CSheetId sheetId= CSheetId(itemImage->getSheetID());
CItemSheet *mpSheet= dynamic_cast<CItemSheet*>(SheetMngr.get(sheetId)); CItemSheet *mpSheet= dynamic_cast<CItemSheet*>(SheetMngr.get(sheetId));
if( isMpAvailable(mpSheet, i) ) if( isMpAvailable(mpSheet, invId, i) && !bLockedByOwner)
{ {
_InventoryMirror[i].Sheet= sheetId; _InventoryMirror[i].Sheet= sheetId;
_InventoryMirror[i].Quality= itemImage->getQuality(); _InventoryMirror[i].Quality= itemImage->getQuality();
@ -422,6 +463,7 @@ void CActionPhraseFaber::validateFaberPlanSelection(CSBrickSheet *itemPlanBrick
_InventoryMirror[i].Weight= itemImage->getWeight(); _InventoryMirror[i].Weight= itemImage->getWeight();
// Bkup original quantity from inventory // Bkup original quantity from inventory
_InventoryMirror[i].OriginalQuantity= _InventoryMirror[i].Quantity; _InventoryMirror[i].OriginalQuantity= _InventoryMirror[i].Quantity;
_InventoryMirror[i].LockedByOwner= bLockedByOwner;
} }
} }
} }
@ -1311,17 +1353,22 @@ void CActionPhraseFaber::onInventoryChange()
return; return;
// Run all the Bag // Run all the Bag
uint invId = 0;
uint indexInInv = 0;
for(i=0;i<_InventoryMirror.size();i++) for(i=0;i<_InventoryMirror.size();i++)
{ {
CItemImage *itemImage= getInvMirrorItemImage(i); CItemImage *itemImage= getInvMirrorItemImage(i, invId, indexInInv);
if(itemImage) if(itemImage)
{ {
CSheetId sheetId= CSheetId(itemImage->getSheetID()); CSheetId sheetId= CSheetId(itemImage->getSheetID());
CItemSheet *mpSheet= dynamic_cast<CItemSheet*>(SheetMngr.get(sheetId)); CItemSheet *mpSheet= dynamic_cast<CItemSheet*>(SheetMngr.get(sheetId));
CItem newInvItem; CItem newInvItem;
// The item must be a mp, and the item must be available bool bLockedByOwner = itemImage->getLockedByOwner();
if( isMpAvailable(mpSheet, i) )
// The item must be a mp, and the item must be available and unlocked
if( isMpAvailable(mpSheet, invId, i) && !bLockedByOwner)
{ {
newInvItem.Sheet= sheetId; newInvItem.Sheet= sheetId;
newInvItem.Quality= itemImage->getQuality(); newInvItem.Quality= itemImage->getQuality();
@ -1329,12 +1376,13 @@ void CActionPhraseFaber::onInventoryChange()
newInvItem.UserColor= itemImage->getUserColor(); newInvItem.UserColor= itemImage->getUserColor();
newInvItem.Weight= itemImage->getWeight(); newInvItem.Weight= itemImage->getWeight();
newInvItem.OriginalQuantity= newInvItem.Quantity; newInvItem.OriginalQuantity= newInvItem.Quantity;
newInvItem.LockedByOwner = bLockedByOwner;
} }
/* There is 4 cases: /* There is 5 cases:
- no changes => no op. - no changes => no op.
- new Mp on a empty or non Mp slot. Easy, just add. - new/unlocked Mp on a empty or non Mp slot. Easy, just add.
- old Mp removed (not same sheetId/quality/userColor) - old Mp removed (not same sheetId/quality/userColor/locked)
- old Mp with quantity changed to be greater - old Mp with quantity changed to be greater
- old Mp with quantity changed to be smaller - old Mp with quantity changed to be smaller
*/ */
@ -1348,8 +1396,8 @@ void CActionPhraseFaber::onInventoryChange()
// If the item was not a mp // If the item was not a mp
if(_InventoryMirror[i].Sheet==CSheetId::Unknown) if(_InventoryMirror[i].Sheet==CSheetId::Unknown)
{ {
// if now it is, easy, just add // if now it is, easy, just add if not locked
if(newInvItem.Sheet!=CSheetId::Unknown) if(newInvItem.Sheet!=CSheetId::Unknown && !newInvItem.LockedByOwner)
curInvItem= newInvItem; curInvItem= newInvItem;
} }
// else must test change or remove // else must test change or remove
@ -1358,7 +1406,8 @@ void CActionPhraseFaber::onInventoryChange()
bool sameMp; bool sameMp;
sameMp= curInvItem.Sheet == newInvItem.Sheet && sameMp= curInvItem.Sheet == newInvItem.Sheet &&
curInvItem.Quality == newInvItem.Quality && curInvItem.Quality == newInvItem.Quality &&
curInvItem.UserColor == newInvItem.UserColor ; curInvItem.UserColor == newInvItem.UserColor &&
curInvItem.LockedByOwner == newInvItem.LockedByOwner;
// if the Mp was deleted from this slot, delete it from all faber execution // if the Mp was deleted from this slot, delete it from all faber execution
if(!sameMp) if(!sameMp)

@ -92,6 +92,7 @@ private:
uint Selected; uint Selected;
// This is the original quantity in inventory // This is the original quantity in inventory
sint32 OriginalQuantity; sint32 OriginalQuantity;
bool LockedByOwner;
CItem() : Sheet(0) CItem() : Sheet(0)
{ {
@ -233,8 +234,8 @@ private:
void removeMpSlotThatUseInvSlot(uint invSlot, uint quantityToRemove); void removeMpSlotThatUseInvSlot(uint invSlot, uint quantityToRemove);
// from an index in _InventoryMirror, get the ItemImage // from an index in _InventoryMirror, get the ItemImage
CItemImage *getInvMirrorItemImage(uint slotIndex); CItemImage *getInvMirrorItemImage(uint slotIndex, uint& invId, uint& indexInInv);
bool isMpAvailable(CItemSheet *mpSheet, uint slotIndex) const; bool isMpAvailable(CItemSheet *mpSheet, uint invId, uint slotIndex) const;
void updateItemResult(); void updateItemResult();
}; };

@ -48,6 +48,7 @@
#include "../sheet_manager.h" #include "../sheet_manager.h"
#include "../user_entity.h" #include "../user_entity.h"
#include "view_bitmap.h" #include "view_bitmap.h"
#include "nel/misc/common.h"
using namespace std::rel_ops; using namespace std::rel_ops;
@ -996,7 +997,7 @@ void CBotChatPageTrade::startSellDialog(CDBCtrlSheet *sheet, CCtrlBase * /* pCal
CCtrlTextButton *confirmButton = dynamic_cast<CCtrlTextButton*>(ig->getCtrl("ok")); CCtrlTextButton *confirmButton = dynamic_cast<CCtrlTextButton*>(ig->getCtrl("ok"));
if (confirmButton) if (confirmButton)
{ {
confirmButton->setActive( true ); confirmButton->setActive( sheet->getLockedByOwner() );
confirmButton->setText(CI18N::get("uiSellImmediately")); confirmButton->setText(CI18N::get("uiSellImmediately"));
confirmButton->setDefaultContextHelp(CI18N::get("uittDirectSellButton")); confirmButton->setDefaultContextHelp(CI18N::get("uittDirectSellButton"));
} }
@ -1538,10 +1539,12 @@ void CBotChatPageTrade::setupResellGroup(bool sellMode, uint defaultQuantity, CI
CViewText *vt= dynamic_cast<CViewText*>(cantResellGroup->getView("reason")); CViewText *vt= dynamic_cast<CViewText*>(cantResellGroup->getView("reason"));
if(vt) if(vt)
{ {
if(resaleFlag==BOTCHATTYPE::ResaleKOBroken) if(resaleFlag == BOTCHATTYPE::ResaleKOBroken)
vt->setHardText("uiCantResaleCauseDamaged"); vt->setHardText("uiCantResaleCauseDamaged");
else else if (resaleFlag == BOTCHATTYPE::ResaleKONoTimeLeft)
vt->setHardText("uiCantResaleCauseTooLate"); vt->setHardText("uiCantResaleCauseTooLate");
else
vt->setHardText("uiCantResaleLockedByOwner");
} }
} }
// else setup "can_resell:choose_resell group" // else setup "can_resell:choose_resell group"
@ -2575,9 +2578,9 @@ static DECLARE_INTERFACE_USER_FCT(getPriceWithFame)
if(value==-1) if(value==-1)
result.setUCString(CI18N::get("uiBadPrice")); result.setUCString(CI18N::get("uiBadPrice"));
else if(value==valueFame) else if(value==valueFame)
result.setUCString(toString(value)); result.setUCString(NLMISC::formatThousands(toString(value)));
else else
result.setUCString(toString("%d (%d)", valueFame, value)); result.setUCString(NLMISC::formatThousands(toString(valueFame)) + " (" + NLMISC::formatThousands(toString(value)) + ")");
return true; return true;
} }
@ -2593,7 +2596,7 @@ static DECLARE_INTERFACE_USER_FCT(getBonusOnResale)
sint valueHigh= (sint)args[0].getInteger(); sint valueHigh= (sint)args[0].getInteger();
sint valueLow= (sint)args[1].getInteger(); sint valueLow= (sint)args[1].getInteger();
sint diff = valueHigh - valueLow; sint diff = valueHigh - valueLow;
result.setUCString(toString("+%d", diff)); result.setUCString("+" + NLMISC::formatThousands(toString(diff)));
return true; return true;
} }

@ -378,7 +378,7 @@ void CChatTargetFilter::setTargetGroup(CChatGroup::TGroupType groupType, uint32
const bool guildActive = pIM->getDbProp("SERVER:GUILD:NAME")->getValueBool(); const bool guildActive = pIM->getDbProp("SERVER:GUILD:NAME")->getValueBool();
switch(groupType) switch(groupType)
{ {
case CChatGroup::dyn_chat: entry+="DYN"; break; case CChatGroup::dyn_chat: entry+="DYN:" + NLMISC::toString(dynamicChannelDbIndex); break;
case CChatGroup::say: entry+="SAY"; break; case CChatGroup::say: entry+="SAY"; break;
case CChatGroup::shout: entry+="SHOUT"; break; case CChatGroup::shout: entry+="SHOUT"; break;
case CChatGroup::team: if(!teamActive) return; entry+="GROUP"; break; case CChatGroup::team: if(!teamActive) return; entry+="GROUP"; break;

@ -148,18 +148,43 @@ CViewBase *CChatTextManager::createMsgText(const ucstring &cstMsg, NLMISC::CRGBA
vt->setMultiLineSpace(getTextMultiLineSpace()); vt->setMultiLineSpace(getTextMultiLineSpace());
vt->setModulateGlobalColor(false); vt->setModulateGlobalColor(false);
ucstring cur_time = "";
static CCDBNodeLeaf* node = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false);
if (node)
{
if (node->getValueBool())
{
cur_time = CInterfaceManager::getTimestampHuman();
}
}
// if text contain any color code, set the text formated and white, // if text contain any color code, set the text formated and white,
// otherwise, set text normal and apply global color // otherwise, set text normal and apply global color
if (msg.find(ucstring("@{")) != ucstring::npos) size_t codePos = msg.find(ucstring("@{"));
if (codePos != ucstring::npos)
{
// Prepend the current time (do it after the color if the color at first position.
if (codePos == 0)
{ {
codePos = msg.find(ucstring("}"));
msg = msg.substr(0, codePos + 1) + cur_time + msg.substr(codePos + 1, msg.length() - codePos);
}
else
{
msg = cur_time + msg;
}
vt->setTextFormatTaged(msg); vt->setTextFormatTaged(msg);
vt->setColor(NLMISC::CRGBA::White); vt->setColor(NLMISC::CRGBA::White);
} }
else else
{ {
msg = cur_time + msg;
vt->setText(msg); vt->setText(msg);
vt->setColor(col); vt->setColor(col);
} }
if (!commandGroup) if (!commandGroup)
{ {
return vt; return vt;

@ -472,15 +472,9 @@ void CChatWindow::displayLocalPlayerTell(const ucstring &receiver, const ucstrin
CInterfaceProperty prop; CInterfaceProperty prop;
prop.readRGBA("UI:SAVE:CHAT:COLORS:SPEAKER"," "); prop.readRGBA("UI:SAVE:CHAT:COLORS:SPEAKER"," ");
encodeColorTag(prop.getRGBA(), finalMsg, false); encodeColorTag(prop.getRGBA(), finalMsg, false);
ucstring cur_time;
CCDBNodeLeaf *pNL = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false); ucstring csr = CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw()) ? "(CSR) " : "";
if (pNL && pNL->getValueBool()) finalMsg += csr + CI18N::get("youTell") + ": ";
{
cur_time = CInterfaceManager::getTimestampHuman();
}
ucstring csr;
if (CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw())) csr += ucstring("(CSR) ");
finalMsg += cur_time + csr + CI18N::get("youTell") + ": ";
prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," "); prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," ");
encodeColorTag(prop.getRGBA(), finalMsg, true); encodeColorTag(prop.getRGBA(), finalMsg, true);
finalMsg += msg; finalMsg += msg;
@ -1294,8 +1288,18 @@ public:
CChatWindow::_ChatWindowLaunchingCommand = chat; CChatWindow::_ChatWindowLaunchingCommand = chat;
string str = text.toUtf8(); string str = text.toUtf8();
string cmdWithArgs = str.substr(1); string cmdWithArgs = str.substr(1);
/* In the chat context, only ' ' is a possible separator */
// Get the command name from the string, can contain spaces
string cmd = cmdWithArgs.substr(0, cmdWithArgs.find(' ')); string cmd = cmdWithArgs.substr(0, cmdWithArgs.find(' '));
if (cmdWithArgs.find('"') == 0)
{
string::size_type pos = cmdWithArgs.find('"', 1);
if (string::npos != pos)
{
cmd = cmdWithArgs.substr(1, pos - 1);
}
}
if ( NLMISC::ICommand::exists( cmd ) ) if ( NLMISC::ICommand::exists( cmd ) )
{ {
NLMISC::ICommand::execute( cmdWithArgs, g_log ); NLMISC::ICommand::execute( cmdWithArgs, g_log );
@ -1314,7 +1318,7 @@ public:
} }
} }
// Clear input string // Clear input string
pEB->setInputString (string("")); pEB->setInputString (ucstring(""));
CGroupContainer *gc = pEB->getEnclosingContainer(); CGroupContainer *gc = pEB->getEnclosingContainer();
if (gc) if (gc)
{ {

@ -115,6 +115,7 @@ public:
// @{ // @{
// Event part // Event part
void setActionOnLeftClick (const std::string &actionHandlerName) { _AHOnLeftClickString = actionHandlerName; _AHOnLeftClick = getAH(actionHandlerName, _AHLeftClickParams); } void setActionOnLeftClick (const std::string &actionHandlerName) { _AHOnLeftClickString = actionHandlerName; _AHOnLeftClick = getAH(actionHandlerName, _AHLeftClickParams); }
void setActionOnLeftClickParams(const std::string &params) { _AHOnLeftClickStringParams = params; }
void setActionOnRightClick (const std::string &actionHandlerName) { _AHOnRightClick = getAH(actionHandlerName, _AHRightClickParams); } void setActionOnRightClick (const std::string &actionHandlerName) { _AHOnRightClick = getAH(actionHandlerName, _AHRightClickParams); }
void setActionOnClockTick (const std::string &ahName) { _AHOnClockTick = getAH(ahName, _AHClockTickParams); } void setActionOnClockTick (const std::string &ahName) { _AHOnClockTick = getAH(ahName, _AHClockTickParams); }
void setParamsOnLeftClick (const std::string &paramsHandlerName) { _AHLeftClickParams = paramsHandlerName; } void setParamsOnLeftClick (const std::string &paramsHandlerName) { _AHLeftClickParams = paramsHandlerName; }
@ -204,6 +205,7 @@ protected:
IActionHandler *_AHOnOver; IActionHandler *_AHOnOver;
CStringShared _AHOverParams; CStringShared _AHOverParams;
std::string _AHOnLeftClickString; std::string _AHOnLeftClickString;
std::string _AHOnLeftClickStringParams;
IActionHandler *_AHOnLeftClick; IActionHandler *_AHOnLeftClick;
CStringShared _AHLeftClickParams; CStringShared _AHLeftClickParams;
IActionHandler *_AHOnLeftDblClick; IActionHandler *_AHOnLeftDblClick;

@ -337,8 +337,15 @@ void CCtrlButton::fitTexture()
bool CCtrlButton::getMouseOverShape(string &texName, uint8 &rot, CRGBA &col) bool CCtrlButton::getMouseOverShape(string &texName, uint8 &rot, CRGBA &col)
{ {
if (_AHOnLeftClickString == "browse") if (_AHOnLeftClickString == "browse")
{
if (!_AHOnLeftClickStringParams.empty())
{
texName = "@curs_pick.tga@"+_AHOnLeftClickStringParams;
}
else
{ {
texName = "curs_pick.tga"; texName = "curs_pick.tga";
}
rot= 0; rot= 0;
col = CRGBA::White; col = CRGBA::White;
return true; return true;

@ -45,6 +45,7 @@
#include "../client_sheets/sphrase_sheet.h" #include "../client_sheets/sphrase_sheet.h"
#include "game_share/xml_auto_ptr.h" #include "game_share/xml_auto_ptr.h"
#include "lua_ihm.h" #include "lua_ihm.h"
#include "game_share/bot_chat_types.h"
#include "../r2/editor.h" #include "../r2/editor.h"
@ -123,6 +124,14 @@ ucstring CControlSheetTooltipInfoWaiter::infoValidated(CDBCtrlSheet* ctrlSheet,
return help; return help;
} }
// ***************************************************************************
int CDBCtrlSheet::luaGetDraggedSheet(CLuaState &ls)
{
CLuaIHM::pushUIOnStack(ls, dynamic_cast<CInterfaceElement *>(_LastDraggedSheet));
return 1;
}
// *************************************************************************** // ***************************************************************************
int CDBCtrlSheet::luaGetHpBuff(CLuaState &ls) int CDBCtrlSheet::luaGetHpBuff(CLuaState &ls)
{ {
@ -179,6 +188,62 @@ int CDBCtrlSheet::luaGetName(CLuaState &ls)
return 1; return 1;
} }
// **********************************************************************************************************
class LuaInfoWaiter : public IItemInfoWaiter
{
public:
volatile bool done;
public:
virtual void infoReceived();
};
void LuaInfoWaiter::infoReceived()
{
getInventory().removeItemInfoWaiter(this);
this->done = true;
}
static LuaInfoWaiter luaInfoWaiter;
// ***************************************************************************
int CDBCtrlSheet::luaGetCreatorName(CLuaState &ls)
{
uint32 itemSlotId = getInventory().getItemSlotId(this);
CClientItemInfo itemInfo = getInventory().getItemInfo(itemSlotId);
ucstring creatorName;
STRING_MANAGER::CStringManagerClient::instance()->getString(itemInfo.CreatorName, creatorName);
CLuaIHM::push(ls, creatorName);
return 1;
}
// ***************************************************************************
int CDBCtrlSheet::luaWaitInfo(CLuaState &ls)
{
static bool sent = false;
CDBCtrlSheet *ctrlSheet = const_cast<CDBCtrlSheet*>(this);
uint32 itemSlotId= getInventory().getItemSlotId(ctrlSheet);
CClientItemInfo itemInfo = getInventory().getItemInfo(itemSlotId);
if (sent || itemInfo.versionInfo != 0)
{
ls.push((bool)(luaInfoWaiter.done));
if (luaInfoWaiter.done)
sent = false;
return luaInfoWaiter.done ? 1 : 0;
}
else
{
luaInfoWaiter.ItemSlotId = itemSlotId;
luaInfoWaiter.ItemSheet = this->getSheetId();
luaInfoWaiter.done = false;
getInventory().addItemInfoWaiter(&luaInfoWaiter);
sent = true;
}
return 0;
}
// *************************************************************************** // ***************************************************************************
int CDBCtrlSheet::luaBuildCrystallizedSpellListBrick(CLuaState &ls) int CDBCtrlSheet::luaBuildCrystallizedSpellListBrick(CLuaState &ls)
@ -1796,10 +1861,18 @@ void CDBCtrlSheet::draw()
{ {
string params = string("src=") + pCSSrc->getId(); string params = string("src=") + pCSSrc->getId();
if (!_AHCanDropParams.empty()) if (!_AHCanDropParams.empty())
{
if (getAHName(_AHOnCanDrop) == "lua")
{
params = _AHCanDropParams;
strFindReplace(params, "%src", pCSSrc->getId());
}
else
{ {
string sTmp = _AHCanDropParams; string sTmp = _AHCanDropParams;
params = sTmp + "|" + params; params = sTmp + "|" + params;
} }
}
pIM->runActionHandler (_AHOnCanDrop, this, params); pIM->runActionHandler (_AHOnCanDrop, this, params);
} }
} }
@ -2138,6 +2211,12 @@ void CDBCtrlSheet::drawSheet (sint32 x, sint32 y, bool draging, bool showSelecti
// if a raw material for example, must add special icon text. // if a raw material for example, must add special icon text.
displayCharBitmaps(_RenderLayer+2, x, y, curSheetColor); displayCharBitmaps(_RenderLayer+2, x, y, curSheetColor);
// Add the lock overlay if needed
if (getLockedByOwner())
{
rVR.draw11RotFlipBitmap (_RenderLayer+1, x - 2, y + 8, 0, false, rVR.getSystemTextureId(CViewRenderer::ItemLockedByOwnerTexture), curSheetColor);
}
} }
break; break;
// Action // Action
@ -2599,10 +2678,18 @@ bool CDBCtrlSheet::handleEvent (const CEventDescriptor &event)
pCSdest->_CanDrop= false; pCSdest->_CanDrop= false;
string params = string("src=") + _Id; string params = string("src=") + _Id;
if (!pCSdest->_AHCanDropParams.empty()) if (!pCSdest->_AHCanDropParams.empty())
{
if (getAHName(pCSdest->_AHOnCanDrop) == "lua")
{
params = pCSdest->_AHCanDropParams;
strFindReplace(params, "%src", _Id);
}
else
{ {
string sTmp = pCSdest->_AHCanDropParams; string sTmp = pCSdest->_AHCanDropParams;
params = sTmp + "|" + params; params = sTmp + "|" + params;
} }
}
pIM->runActionHandler (pCSdest->_AHOnCanDrop, pCSdest, params); pIM->runActionHandler (pCSdest->_AHOnCanDrop, pCSdest, params);
// Drop only if canDrop. // Drop only if canDrop.
@ -2611,9 +2698,17 @@ bool CDBCtrlSheet::handleEvent (const CEventDescriptor &event)
// build params // build params
string params = string("src=") + _Id; string params = string("src=") + _Id;
if (!pCSdest->_AHDropParams.empty()) if (!pCSdest->_AHDropParams.empty())
{
if (getAHName(pCSdest->_AHOnDrop) == "lua")
{
params = pCSdest->_AHDropParams;
strFindReplace(params, "%src", _Id);
}
else
{ {
string sTmp = pCSdest->_AHDropParams; string sTmp = pCSdest->_AHDropParams;
params = sTmp + "|" + params; // must copy 'drop' params at start because it could be the name of a procedure params = sTmp + "|" + params;// must copy 'drop' params at start because it could be the name of a procedure
}
} }
// call action // call action
pIM->runActionHandler (pCSdest->_AHOnDrop, pCSdest, params); pIM->runActionHandler (pCSdest->_AHOnDrop, pCSdest, params);
@ -2648,10 +2743,18 @@ bool CDBCtrlSheet::handleEvent (const CEventDescriptor &event)
pList->setCanDrop(false); pList->setCanDrop(false);
string params = string("src=") + _Id; string params = string("src=") + _Id;
if (!pList->getCtrlSheetInfo()._AHCanDropParams.empty()) if (!pList->getCtrlSheetInfo()._AHCanDropParams.empty())
{
if (getAHName(pList->getCtrlSheetInfo()._AHOnCanDrop) == "lua")
{
params = pList->getCtrlSheetInfo()._AHCanDropParams;
strFindReplace(params, "%src", _Id);
}
else
{ {
string sTmp = pList->getCtrlSheetInfo()._AHCanDropParams; string sTmp = pList->getCtrlSheetInfo()._AHCanDropParams;
params = sTmp + "|" + params; params = sTmp + "|" + params;
} }
}
pIM->runActionHandler (pList->getCtrlSheetInfo()._AHOnCanDrop, pList, params); pIM->runActionHandler (pList->getCtrlSheetInfo()._AHOnCanDrop, pList, params);
// Drop only if canDrop. // Drop only if canDrop.
@ -2660,10 +2763,18 @@ bool CDBCtrlSheet::handleEvent (const CEventDescriptor &event)
// build params // build params
string params = string("src=") + _Id; string params = string("src=") + _Id;
if (!pList->getCtrlSheetInfo()._AHDropParams.empty()) if (!pList->getCtrlSheetInfo()._AHDropParams.empty())
{
if (getAHName(pList->getCtrlSheetInfo()._AHOnDrop) == "lua")
{
params = pList->getCtrlSheetInfo()._AHDropParams;
strFindReplace(params, "%src", _Id);
}
else
{ {
string sTmp = pList->getCtrlSheetInfo()._AHDropParams; string sTmp = pList->getCtrlSheetInfo()._AHDropParams;
params = sTmp + "|" + params; // must copy 'drop' params at start because it could be the name of a procedure params = sTmp + "|" + params; // must copy 'drop' params at start because it could be the name of a procedure
} }
}
// call action // call action
pIM->runActionHandler (pList->getCtrlSheetInfo()._AHOnDrop, pList, params); pIM->runActionHandler (pList->getCtrlSheetInfo()._AHOnDrop, pList, params);
handled = true; handled = true;
@ -2975,9 +3086,32 @@ void CDBCtrlSheet::getContextHelp(ucstring &help) const
} }
else if(getType() == CCtrlSheetInfo::SheetType_Item) else if(getType() == CCtrlSheetInfo::SheetType_Item)
{ {
const CItemSheet *item = asItemSheet(); const CItemSheet *item= asItemSheet();
if (item) if(item)
help = getItemActualName(); {
if (item->Family == ITEMFAMILY::CRYSTALLIZED_SPELL || item->Family == ITEMFAMILY::JEWELRY || item->Family == ITEMFAMILY::ARMOR)
{
string luaMethodName = ( (item->Family == ITEMFAMILY::CRYSTALLIZED_SPELL) ? "updateCrystallizedSpellTooltip" : "updateBuffItemTooltip");
CDBCtrlSheet *ctrlSheet = const_cast<CDBCtrlSheet*>(this);
if ( ! getInventory().isItemInfoUpToDate(getInventory().getItemSlotId(ctrlSheet)))
{
// Prepare the waiter
ControlSheetTooltipUpdater.ItemSheet= ctrlSheet->getSheetId();
ControlSheetTooltipUpdater.LuaMethodName = luaMethodName;
ControlSheetTooltipUpdater.ItemSlotId= getInventory().getItemSlotId(ctrlSheet);
ControlSheetTooltipUpdater.CtrlSheet = ctrlSheet;
// Add the waiter
getInventory().addItemInfoWaiter(&ControlSheetTooltipUpdater);
}
help = ControlSheetTooltipUpdater.infoValidated(ctrlSheet, luaMethodName);
}
else
help= getItemActualName();
}
else else
help= _ContextHelp; help= _ContextHelp;
} }
@ -3936,6 +4070,17 @@ void CDBCtrlSheet::setItemResaleFlag(sint32 rf)
node->setValue32(rf); node->setValue32(rf);
} }
// ***************************************************************************
bool CDBCtrlSheet::getLockedByOwner() const
{
return (getItemResaleFlag() == BOTCHATTYPE::ResaleKOLockedByOwner);
}
// ***************************************************************************
bool CDBCtrlSheet::canOwnerLock() const
{
return (NULL != getItemResaleFlagPtr());
}
// *************************************************************************** // ***************************************************************************
sint32 CDBCtrlSheet::getItemSellerType() const sint32 CDBCtrlSheet::getItemSellerType() const

@ -194,16 +194,20 @@ public:
void setActionOnLeftClick (const std::string &ActionHandlerName) { _AHOnLeftClick = getAH(ActionHandlerName, _AHLeftClickParams); } void setActionOnLeftClick (const std::string &ActionHandlerName) { _AHOnLeftClick = getAH(ActionHandlerName, _AHLeftClickParams); }
void setActionOnRightClick (const std::string &ActionHandlerName) { _AHOnRightClick = getAH(ActionHandlerName, _AHRightClickParams); } void setActionOnRightClick (const std::string &ActionHandlerName) { _AHOnRightClick = getAH(ActionHandlerName, _AHRightClickParams); }
void setActionOnDrop (const std::string &ActionHandlerName) { _AHOnDrop = getAH(ActionHandlerName, _AHDropParams); } void setActionOnDrop (const std::string &ActionHandlerName) { _AHOnDrop = getAH(ActionHandlerName, _AHDropParams); }
void setActionOnCanDrop (const std::string &ActionHandlerName) { _AHOnCanDrop = getAH(ActionHandlerName, _AHCanDropParams); }
void setParamsOnLeftClick (const std::string &ParamsHandlerName) { _AHLeftClickParams = ParamsHandlerName; } void setParamsOnLeftClick (const std::string &ParamsHandlerName) { _AHLeftClickParams = ParamsHandlerName; }
void setParamsOnRightClick (const std::string &ParamsHandlerName) { _AHRightClickParams = ParamsHandlerName; } void setParamsOnRightClick (const std::string &ParamsHandlerName) { _AHRightClickParams = ParamsHandlerName; }
void setParamsOnDrop (const std::string &ParamsHandlerName) { _AHDropParams = ParamsHandlerName; } void setParamsOnDrop (const std::string &ParamsHandlerName) { _AHDropParams = ParamsHandlerName; }
void setParamsOnCanDrop (const std::string &ParamsHandlerName) { _AHCanDropParams = ParamsHandlerName; }
const std::string &getActionOnLeftClick () const { return getAHName(_AHOnLeftClick); } const std::string &getActionOnLeftClick () const { return getAHName(_AHOnLeftClick); }
const std::string &getActionOnRightClick () const { return getAHName(_AHOnRightClick); } const std::string &getActionOnRightClick () const { return getAHName(_AHOnRightClick); }
const std::string &getActionOnDrop () const { return getAHName(_AHOnDrop); } const std::string &getActionOnDrop () const { return getAHName(_AHOnDrop); }
const std::string &getActionOnCanDrop () const { return getAHName(_AHOnCanDrop); }
const std::string &getParamsOnLeftClick () const { return _AHLeftClickParams; } const std::string &getParamsOnLeftClick () const { return _AHLeftClickParams; }
const std::string &getParamsOnRightClick () const { return _AHRightClickParams; } const std::string &getParamsOnRightClick () const { return _AHRightClickParams; }
const std::string &getParamsOnDrop () const { return _AHDropParams; } const std::string &getParamsOnDrop () const { return _AHDropParams; }
const std::string &getParamsOnCanDrop () const { return _AHCanDropParams; }
void setListMenuLeft (const std::string &cm) { CCtrlSheetInfo::setListMenuLeft(cm); } void setListMenuLeft (const std::string &cm) { CCtrlSheetInfo::setListMenuLeft(cm); }
void setListMenuRight (const std::string &cm) { CCtrlSheetInfo::setListMenuRight(cm); } void setListMenuRight (const std::string &cm) { CCtrlSheetInfo::setListMenuRight(cm); }
@ -215,6 +219,7 @@ public:
void setCanDrop (bool cd) { _CanDrop = cd; } void setCanDrop (bool cd) { _CanDrop = cd; }
bool getCanDrop () const { return _CanDrop; } bool getCanDrop () const { return _CanDrop; }
bool isDragable() { return _Dragable; } bool isDragable() { return _Dragable; }
void setDragable(bool dragable) { _Dragable = dragable; }
bool isDraging() { return _Draging; } bool isDraging() { return _Draging; }
sint32 getDeltaDragX() {return _DeltaDragX;} sint32 getDeltaDragX() {return _DeltaDragX;}
sint32 getDeltaDragY() {return _DeltaDragY;} sint32 getDeltaDragY() {return _DeltaDragY;}
@ -265,19 +270,35 @@ public:
REFLECT_SINT32("back", getGuildBack, setGuildBack); REFLECT_SINT32("back", getGuildBack, setGuildBack);
REFLECT_SINT32("symbol", getGuildSymbol, setGuildSymbol); REFLECT_SINT32("symbol", getGuildSymbol, setGuildSymbol);
REFLECT_BOOL("invert_symbol", getInvertGuildSymbol, setInvertGuildSymbol); REFLECT_BOOL("invert_symbol", getInvertGuildSymbol, setInvertGuildSymbol);
REFLECT_BOOL("dragable", isDragable, setDragable);
REFLECT_BOOL("can_drop", getCanDrop, setCanDrop);
REFLECT_STRING ("left_click", getActionOnLeftClick, setActionOnLeftClick);
REFLECT_STRING ("right_click", getActionOnRightClick, setActionOnRightClick);
REFLECT_STRING ("left_click_params", getParamsOnLeftClick, setParamsOnLeftClick);
REFLECT_STRING ("right_click_params", getParamsOnRightClick, setParamsOnRightClick);
REFLECT_STRING ("on_drop", getActionOnDrop, setActionOnDrop);
REFLECT_STRING ("on_drop_params", getParamsOnDrop, setParamsOnDrop);
REFLECT_STRING ("on_can_drop", getActionOnCanDrop, setActionOnCanDrop);
REFLECT_STRING ("on_can_drop_params", getParamsOnCanDrop, setParamsOnCanDrop);
REFLECT_LUA_METHOD("getDraggedSheet", luaGetDraggedSheet)
REFLECT_LUA_METHOD("getHpBuff", luaGetHpBuff) REFLECT_LUA_METHOD("getHpBuff", luaGetHpBuff)
REFLECT_LUA_METHOD("getSapBuff", luaGetSapBuff) REFLECT_LUA_METHOD("getSapBuff", luaGetSapBuff)
REFLECT_LUA_METHOD("getFocusBuff", luaGetFocusBuff) REFLECT_LUA_METHOD("getFocusBuff", luaGetFocusBuff)
REFLECT_LUA_METHOD("getStaBuff", luaGetStaBuff) REFLECT_LUA_METHOD("getStaBuff", luaGetStaBuff)
REFLECT_LUA_METHOD("getName", luaGetName) REFLECT_LUA_METHOD("getName", luaGetName)
REFLECT_LUA_METHOD("getCreatorName", luaGetCreatorName)
REFLECT_LUA_METHOD("waitInfo", luaWaitInfo)
REFLECT_LUA_METHOD("buildCrystallizedSpellListBrick", luaBuildCrystallizedSpellListBrick) REFLECT_LUA_METHOD("buildCrystallizedSpellListBrick", luaBuildCrystallizedSpellListBrick)
REFLECT_EXPORT_END REFLECT_EXPORT_END
int luaGetDraggedSheet(CLuaState &ls);
int luaGetHpBuff(CLuaState &ls); int luaGetHpBuff(CLuaState &ls);
int luaGetSapBuff(CLuaState &ls); int luaGetSapBuff(CLuaState &ls);
int luaGetFocusBuff(CLuaState &ls); int luaGetFocusBuff(CLuaState &ls);
int luaGetStaBuff(CLuaState &ls); int luaGetStaBuff(CLuaState &ls);
int luaGetName(CLuaState &ls); int luaGetName(CLuaState &ls);
int luaGetCreatorName(CLuaState &ls);
int luaWaitInfo(CLuaState &ls);
int luaBuildCrystallizedSpellListBrick(CLuaState &ls); int luaBuildCrystallizedSpellListBrick(CLuaState &ls);
// hardcode creation. User must setup other CtrlBase value (parent etc...) // hardcode creation. User must setup other CtrlBase value (parent etc...)
@ -355,9 +376,9 @@ public:
/// Special ContextHelp for ctrl sheet. /// Special ContextHelp for ctrl sheet.
virtual void getContextHelp(ucstring &help) const; virtual void getContextHelp(ucstring &help) const;
/// Special ContextHelp for ctrl sheet.
virtual void getContextHelpToolTip(ucstring &help) const; virtual void getContextHelpToolTip(ucstring &help) const;
/** true if an item of another ctrlSheet can be dropped on this slot. /** true if an item of another ctrlSheet can be dropped on this slot.
* also return true if src is 0, or if _ItemSlot==UNDEFINED * also return true if src is 0, or if _ItemSlot==UNDEFINED
*/ */
@ -494,6 +515,12 @@ public:
// set item RESALE_FLAG // set item RESALE_FLAG
void setItemResaleFlag(sint32 rf); void setItemResaleFlag(sint32 rf);
// get item locked by owner
bool getLockedByOwner() const;
// true if the inventory supports owner locking
bool canOwnerLock() const;
// get item SELLER_TYPE. 0 if no DB // get item SELLER_TYPE. 0 if no DB
sint32 getItemSellerType() const; sint32 getItemSellerType() const;
CCDBNodeLeaf *getItemSellerTypePtr() const; CCDBNodeLeaf *getItemSellerTypePtr() const;

@ -30,6 +30,7 @@
#include "game_share/pvp_clan.h" #include "game_share/pvp_clan.h"
#include "../string_manager_client.h" #include "../string_manager_client.h"
#include "../entity_cl.h" #include "../entity_cl.h"
#include "nel/misc/common.h"
using namespace NLMISC; using namespace NLMISC;
@ -264,7 +265,7 @@ void CDBGroupListSheetTrade::CSheetChildTrade::updateViewText(CDBGroupListSheetT
{ {
STRING_MANAGER::CStringManagerClient *pSMC = STRING_MANAGER::CStringManagerClient::instance(); STRING_MANAGER::CStringManagerClient *pSMC = STRING_MANAGER::CStringManagerClient::instance();
text += string("\n") + pSMC->getOutpostBuildingLocalizedDescription(CSheetId(Ctrl->getSheetId())); text += string("\n") + pSMC->getOutpostBuildingLocalizedDescription(CSheetId(Ctrl->getSheetId()));
text += "\n" + CI18N::get("uiBotChatPrice") + toString(pOBS->CostDapper); text += "\n" + CI18N::get("uiBotChatPrice") + NLMISC::formatThousands(toString(pOBS->CostDapper));
text += CI18N::get("uiBotChatTime") + toString(pOBS->CostTime/60) + CI18N::get("uiBotChatTimeMinute"); text += CI18N::get("uiBotChatTime") + toString(pOBS->CostTime/60) + CI18N::get("uiBotChatTimeMinute");
if ((pOBS->CostTime % 60) != 0) if ((pOBS->CostTime % 60) != 0)
text += toString(pOBS->CostTime%60) + CI18N::get("uiBotChatTimeSecond"); text += toString(pOBS->CostTime%60) + CI18N::get("uiBotChatTimeSecond");
@ -341,7 +342,7 @@ void CDBGroupListSheetTrade::CSheetChildTrade::updateViewText(CDBGroupListSheetT
if (pIS && pIS->Family == ITEMFAMILY::GUILD_OPTION) if (pIS && pIS->Family == ITEMFAMILY::GUILD_OPTION)
{ {
text+= "\n" + CI18N::get("uiBotChatSkillPointCost") + toString(pIS->GuildOption.XPCost); text+= "\n" + CI18N::get("uiBotChatSkillPointCost") + toString(pIS->GuildOption.XPCost);
text+= "\n" + CI18N::get("uiBotChatPrice") + toString(pIS->GuildOption.MoneyCost); text+= "\n" + CI18N::get("uiBotChatPrice") + NLMISC::formatThousands(toString(pIS->GuildOption.MoneyCost));
guildOption= true; guildOption= true;
} }
} }
@ -376,10 +377,10 @@ void CDBGroupListSheetTrade::CSheetChildTrade::updateViewText(CDBGroupListSheetT
if (LastPrice > 0) if (LastPrice > 0)
{ {
if(displayMulPrice) if(displayMulPrice)
text+= "\n" + CI18N::get("uiBotChatPrice") + toString(sint32(LastPrice * priceFactor)) + " (" text+= "\n" + CI18N::get("uiBotChatPrice") + NLMISC::formatThousands(toString(sint32(LastPrice * priceFactor))) + " ("
+ toString( sint32(factor) * sint32(LastPrice * priceFactor) ) + ")"; + NLMISC::formatThousands(toString( sint32(factor) * sint32(LastPrice * priceFactor) )) + ")";
else else
text+= "\n" + CI18N::get("uiBotChatPrice") + toString( sint32(factor * LastPrice * priceFactor) ); text+= "\n" + CI18N::get("uiBotChatPrice") + NLMISC::formatThousands(toString( sint32(factor * LastPrice * priceFactor) ));
} }
if ((LastFactionPointPrice != 0) && (LastFactionType >= PVP_CLAN::BeginClans) && (LastFactionType <= PVP_CLAN::EndClans)) if ((LastFactionPointPrice != 0) && (LastFactionType >= PVP_CLAN::BeginClans) && (LastFactionType <= PVP_CLAN::EndClans))
@ -390,7 +391,7 @@ void CDBGroupListSheetTrade::CSheetChildTrade::updateViewText(CDBGroupListSheetT
text+= "\n"; text+= "\n";
text+= CI18N::get("uiBotChatFactionType") + PVP_CLAN::toString((PVP_CLAN::TPVPClan)LastFactionType) text+= CI18N::get("uiBotChatFactionType") + PVP_CLAN::toString((PVP_CLAN::TPVPClan)LastFactionType)
+ CI18N::get("uiBotChatFactionPointPrice") + toString(LastFactionPointPrice); + CI18N::get("uiBotChatFactionPointPrice") + NLMISC::formatThousands(toString(LastFactionPointPrice));
} }
// some additional info for resale // some additional info for resale
@ -402,10 +403,10 @@ void CDBGroupListSheetTrade::CSheetChildTrade::updateViewText(CDBGroupListSheetT
{ {
// append price // append price
if(pIS && pIS->Stackable>1 && zeFather->getMultiplyPriceByQuantityFlag()) if(pIS && pIS->Stackable>1 && zeFather->getMultiplyPriceByQuantityFlag())
text+= CI18N::get("uiBotChatRetirePrice") + toString(LastPriceRetire) + " (" text+= CI18N::get("uiBotChatRetirePrice") + NLMISC::formatThousands(toString(LastPriceRetire)) + " ("
+ toString(factor * LastPriceRetire) + ")"; + NLMISC::formatThousands(toString(factor * LastPriceRetire)) + ")";
else else
text+= CI18N::get("uiBotChatRetirePrice") + toString(factor * LastPriceRetire); text+= CI18N::get("uiBotChatRetirePrice") + NLMISC::formatThousands(toString(factor * LastPriceRetire));
// set resale time left // set resale time left
ucstring fmt= CI18N::get("uiBotChatResaleTimeLeft"); ucstring fmt= CI18N::get("uiBotChatResaleTimeLeft");
strFindReplace(fmt, "%d", toString(LastResaleTimeLeft/RYZOM_DAY_IN_HOUR)); strFindReplace(fmt, "%d", toString(LastResaleTimeLeft/RYZOM_DAY_IN_HOUR));
@ -482,6 +483,12 @@ bool CDBGroupListSheetTrade::CSheetChildTrade::isSheetValid(CDBGroupListSheetTex
return false; return false;
} }
// Locked by owner; cannot trade
if (Ctrl->getLockedByOwner())
{
return false;
}
// Check seller type? // Check seller type?
TSellerTypeFilter stf= father->getSellerTypeFilter(); TSellerTypeFilter stf= father->getSellerTypeFilter();
if( stf != None) if( stf != None)

@ -21,6 +21,7 @@
#include "dbview_number.h" #include "dbview_number.h"
#include "interface_manager.h" #include "interface_manager.h"
#include "game_share/xml_auto_ptr.h" #include "game_share/xml_auto_ptr.h"
#include "nel/misc/common.h"
using namespace std; using namespace std;
using namespace NL3D; using namespace NL3D;
@ -102,30 +103,6 @@ bool CDBViewNumber::parse (xmlNodePtr cur, CInterfaceGroup * parentGroup)
return true; return true;
} }
// ***************************************************************************
// Helper function
ucstring formatThousands(const ucstring& s, const ucstring& separator)
{
int j;
int k;
int topI = s.length() - 1;
if (topI < 4) return s;
ucstring ns;
do
{
for (j = topI, k = 0; j >= 0 && k < 3; --j, ++k )
{
ns = s[j] + ns; // new char is added to front of ns
if( j > 0 && k == 2) ns = separator + ns; // j > 0 means still more digits
}
topI -= 3;
} while(topI >= 0);
return ns;
}
// *************************************************************************** // ***************************************************************************
void CDBViewNumber::checkCoords() void CDBViewNumber::checkCoords()
{ {
@ -134,8 +111,7 @@ void CDBViewNumber::checkCoords()
if (_Cache != val) if (_Cache != val)
{ {
_Cache= val; _Cache= val;
static ucstring separator = NLMISC::CI18N::get("uiThousandsSeparator"); ucstring value = _Format ? NLMISC::formatThousands(toString(val)) : toString(val);
ucstring value = _Format ? formatThousands(toString(val), separator) : toString(val);
if (_Positive) setText(val >= 0 ? ( ucstring(_Prefix) + value + ucstring(_Suffix) ) : ucstring("?")); if (_Positive) setText(val >= 0 ? ( ucstring(_Prefix) + value + ucstring(_Suffix) ) : ucstring("?"));
else setText( ucstring(_Prefix) + value + ucstring(_Suffix) ); else setText( ucstring(_Prefix) + value + ucstring(_Suffix) );
} }

@ -34,6 +34,7 @@ extern "C"
#include "view_link.h" #include "view_link.h"
#include "ctrl_scroll.h" #include "ctrl_scroll.h"
#include "ctrl_button.h" #include "ctrl_button.h"
#include "dbctrl_sheet.h"
#include "ctrl_text_button.h" #include "ctrl_text_button.h"
#include "action_handler.h" #include "action_handler.h"
#include "group_paragraph.h" #include "group_paragraph.h"
@ -64,12 +65,54 @@ CGroupHTML *CGroupHTML::_ConnectingLock = NULL;
extern CActionsContext ActionsContext; extern CActionsContext ActionsContext;
// Check if domain is on TrustedDomain // Check if domain is on TrustedDomain
bool CGroupHTML::isTrustedDomain(const string &domain) { bool CGroupHTML::isTrustedDomain(const string &domain)
{
vector<string>::iterator it; vector<string>::iterator it;
it = find (ClientCfg.WebIgTrustedDomains.begin(), ClientCfg.WebIgTrustedDomains.end(), domain); it = find (ClientCfg.WebIgTrustedDomains.begin(), ClientCfg.WebIgTrustedDomains.end(), domain);
return it != ClientCfg.WebIgTrustedDomains.end(); return it != ClientCfg.WebIgTrustedDomains.end();
} }
void CGroupHTML::setImage(CViewBase * view, const string &file)
{
CCtrlButton *btn = dynamic_cast<CCtrlButton*>(view);
if(btn)
{
btn->setTexture (file);
btn->setTexturePushed(file);
btn->invalidateCoords();
btn->invalidateContent();
btn->resetInvalidCoords();
btn->updateCoords();
paragraphChange();
}
else
{
CViewBitmap *btm = dynamic_cast<CViewBitmap*>(view);
if(btm)
{
btm->setTexture (file);
btm->invalidateCoords();
btm->invalidateContent();
btm->resetInvalidCoords();
btm->updateCoords();
paragraphChange();
}
else
{
CGroupCell *btgc = dynamic_cast<CGroupCell*>(view);
if(btgc)
{
btgc->setTexture (file);
btgc->invalidateCoords();
btgc->invalidateContent();
btgc->resetInvalidCoords();
btgc->updateCoords();
paragraphChange();
}
}
}
}
// Get an url and return the local filename with the path where the url image should be // Get an url and return the local filename with the path where the url image should be
string CGroupHTML::localImageName(const string &url) string CGroupHTML::localImageName(const string &url)
{ {
@ -99,30 +142,38 @@ void CGroupHTML::addImageDownload(const string &url, CViewBase *img)
curl_easy_setopt(curl, CURLOPT_NOPROGRESS, true); curl_easy_setopt(curl, CURLOPT_NOPROGRESS, true);
curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); curl_easy_setopt(curl, CURLOPT_URL, url.c_str());
string dest = localImageName(url)+".tmp"; string dest = localImageName(url);
string tmpdest = localImageName(url)+".tmp";
#ifdef LOG_DL #ifdef LOG_DL
nlwarning("add to download '%s' dest '%s' img %p", url.c_str(), dest.c_str(), img); nlwarning("add to download '%s' dest '%s' img %p", url.c_str(), dest.c_str(), img);
#endif #endif
// create the local file
if (NLMISC::CFile::fileExists(dest)) // erase the tmp file if exists
if (NLMISC::CFile::fileExists(tmpdest))
NLMISC::CFile::deleteFile(tmpdest);
if (!NLMISC::CFile::fileExists(dest))
{ {
CFile::setRWAccess(dest);
NLMISC::CFile::deleteFile(dest); FILE *fp = fopen (tmpdest.c_str(), "wb");
}
FILE *fp = fopen (dest.c_str(), "wb");
if (fp == NULL) if (fp == NULL)
{ {
nlwarning("Can't open file '%s' for writing: code=%d '%s'", dest.c_str (), errno, strerror(errno)); nlwarning("Can't open file '%s' for writing: code=%d '%s'", tmpdest.c_str (), errno, strerror(errno));
return; return;
} }
curl_easy_setopt(curl, CURLOPT_FILE, fp); curl_easy_setopt(curl, CURLOPT_FILE, fp);
curl_multi_add_handle(MultiCurl, curl); curl_multi_add_handle(MultiCurl, curl);
Curls.push_back(CDataDownload(curl, url, fp, ImgType, img, "", "")); Curls.push_back(CDataDownload(curl, url, fp, ImgType, img, "", ""));
#ifdef LOG_DL #ifdef LOG_DL
nlwarning("adding handle %x, %d curls", curl, Curls.size()); nlwarning("adding handle %x, %d curls", curl, Curls.size());
#endif #endif
RunningCurls++; RunningCurls++;
}
else
{
setImage(img, dest);
}
} }
void CGroupHTML::initImageDownload() void CGroupHTML::initImageDownload()
@ -297,41 +348,11 @@ void CGroupHTML::checkDownloads()
for(uint i = 0; i < it->imgs.size(); i++) for(uint i = 0; i < it->imgs.size(); i++)
{ {
// don't display image that are not power of 2 // don't display image that are not power of 2
uint32 w, h; //uint32 w, h;
CBitmap::loadSize (file, w, h); //CBitmap::loadSize (file, w, h);
if (w == 0 || h == 0 || ((!NLMISC::isPowerOf2(w) || !NLMISC::isPowerOf2(h)) && !NL3D::CTextureFile::supportNonPowerOfTwoTextures())) //if (w == 0 || h == 0 || ((!NLMISC::isPowerOf2(w) || !NLMISC::isPowerOf2(h)) && !NL3D::CTextureFile::supportNonPowerOfTwoTextures()))
file.clear(); // file.clear();
setImage(it->imgs[i], file);
CCtrlButton *btn = dynamic_cast<CCtrlButton*>(it->imgs[i]);
if(btn)
{
#ifdef LOG_DL
nlwarning("refresh new downloading image %d button %p", i, it->imgs[i]);
#endif
btn->setTexture (file);
btn->setTexturePushed(file);
btn->invalidateCoords();
btn->invalidateContent();
btn->resetInvalidCoords();
btn->updateCoords();
paragraphChange();
}
else
{
CViewBitmap *btm = dynamic_cast<CViewBitmap*>(it->imgs[i]);
if(btm)
{
#ifdef LOG_DL
nlwarning("refresh new downloading image %d image %p", i, it->imgs[i]);
#endif
btm->setTexture (file);
btm->invalidateCoords();
btm->invalidateContent();
btm->resetInvalidCoords();
btm->updateCoords();
paragraphChange();
}
}
} }
} }
} }
@ -446,6 +467,28 @@ void CGroupHTML::beginBuild ()
} }
TStyle CGroupHTML::parseStyle (const string &str_styles)
{
TStyle styles;
vector<string> elements;
NLMISC::splitString(str_styles, ";", elements);
for(uint i = 0; i < elements.size(); ++i)
{
vector<string> style;
NLMISC::splitString(elements[i], ":", style);
if (style.size() >= 2)
{
string fullstyle = style[1];
for (uint j=2; j < style.size(); j++)
fullstyle += ":"+style[j];
styles[trim(style[0])] = fullstyle;
}
}
return styles;
}
// *************************************************************************** // ***************************************************************************
void CGroupHTML::addText (const char * buf, int len) void CGroupHTML::addText (const char * buf, int len)
@ -556,9 +599,31 @@ void CGroupHTML::addLink (uint element_number, uint /* attribute_number */, HTCh
_Link.push_back(""); _Link.push_back("");
} }
} }
for(uint8 i = MY_HTML_A_ACCESSKEY; i < MY_HTML_A_Z_ACTION_SHORTCUT; i++)
{
if (present[i] && value[i])
{
string title = value[i];
// nlinfo("key %d = %s", i, title.c_str());
}
}
//nlinfo("key of TITLE is : %d", MY_HTML_A_Z_ACTION_PARAMS);
if (present[MY_HTML_A_Z_ACTION_PARAMS] && value[MY_HTML_A_Z_ACTION_PARAMS])
{
string title = value[MY_HTML_A_Z_ACTION_PARAMS];
_LinkTitle.push_back(title);
}
else
_LinkTitle.push_back("");
} }
else else
{
_Link.push_back(""); _Link.push_back("");
_LinkTitle.push_back("");
}
} }
} }
} }
@ -626,7 +691,6 @@ static const char *scanColorComponent(const char *src, uint8 &intensity)
return src; return src;
} }
class CNameToCol class CNameToCol
{ {
public: public:
@ -831,6 +895,11 @@ void CGroupHTML::beginElement (uint element_number, const BOOL *present, const c
_GlobalColor.push_back(LinkColorGlobalColor); _GlobalColor.push_back(LinkColorGlobalColor);
_A.push_back(true); _A.push_back(true);
if (present[MY_HTML_A_TITLE] && value[MY_HTML_A_TITLE])
_LinkTitle.push_back(value[MY_HTML_A_TITLE]);
if (present[MY_HTML_A_CLASS] && value[MY_HTML_A_CLASS])
_LinkClass.push_back(value[MY_HTML_A_CLASS]);
// Quick help // Quick help
if (_TrustedDomain && present[MY_HTML_A_Z_ACTION_SHORTCUT] && value[MY_HTML_A_Z_ACTION_SHORTCUT]) if (_TrustedDomain && present[MY_HTML_A_Z_ACTION_SHORTCUT] && value[MY_HTML_A_Z_ACTION_SHORTCUT])
{ {
@ -856,15 +925,87 @@ void CGroupHTML::beginElement (uint element_number, const BOOL *present, const c
} }
} }
} }
break; break;
case HTML_DIV: case HTML_DIV:
{ {
if (present[MY_HTML_DIV_NAME] && value[MY_HTML_DIV_NAME]) if (present[MY_HTML_DIV_NAME] && value[MY_HTML_DIV_NAME])
{
_DivName = value[MY_HTML_DIV_NAME]; _DivName = value[MY_HTML_DIV_NAME];
string instClass;
if (present[MY_HTML_DIV_CLASS] && value[MY_HTML_DIV_CLASS])
instClass = value[MY_HTML_DIV_CLASS];
// use generic template system
if (_TrustedDomain && !instClass.empty() && instClass == "ryzom-ui-grouptemplate")
{
string id;
if (present[MY_HTML_DIV_ID] && value[MY_HTML_DIV_ID])
id = value[MY_HTML_DIV_ID];
string style;
if (present[MY_HTML_DIV_STYLE] && value[MY_HTML_DIV_STYLE])
style = value[MY_HTML_DIV_STYLE];
typedef pair<string, string> TTmplParam;
vector<TTmplParam> tmplParams;
string templateName;
if (!style.empty())
{
TStyle styles = parseStyle(style);
TStyle::iterator it;
for (it=styles.begin(); it != styles.end(); it++)
{
if ((*it).first == "template")
templateName = (*it).second;
else
tmplParams.push_back(TTmplParam((*it).first, (*it).second));
}
}
if (!templateName.empty())
{
string parentId;
bool haveParentDiv = getDiv() != NULL;
if (haveParentDiv)
parentId = getDiv()->getId();
else
parentId = _Paragraph->getId();
CInterfaceManager *im = CInterfaceManager::getInstance();
CInterfaceGroup *inst = im->createGroupInstance(templateName, parentId+":"+id, tmplParams);
if (inst)
{
inst->setId(parentId+":"+id);
inst->updateCoords();
if (haveParentDiv)
{
inst->setParent(getDiv());
inst->setParentSize(getDiv());
inst->setParentPos(getDiv());
inst->setPosRef(Hotspot_TL);
inst->setParentPosRef(Hotspot_TL);
getDiv()->addGroup(inst);
}
else
{
if (!_Paragraph)
{
newParagraph (0);
paragraphChange ();
}
getParagraph()->addChild(inst);
paragraphChange();
}
_Divs.push_back(inst);
}
}
} }
} }
break; break;
case HTML_FONT: case HTML_FONT:
{ {
bool found = false; bool found = false;
@ -898,12 +1039,43 @@ void CGroupHTML::beginElement (uint element_number, const BOOL *present, const c
addString(ucstring ("\n")); addString(ucstring ("\n"));
break; break;
case HTML_BODY: case HTML_BODY:
{
if (present[HTML_BODY_BGCOLOR] && value[HTML_BODY_BGCOLOR]) if (present[HTML_BODY_BGCOLOR] && value[HTML_BODY_BGCOLOR])
{ {
// Get the color
CRGBA bgColor = getColor (value[HTML_BODY_BGCOLOR]); CRGBA bgColor = getColor (value[HTML_BODY_BGCOLOR]);
setBackgroundColor (bgColor); setBackgroundColor (bgColor);
} }
string style;
if (present[HTML_BODY_STYLE] && value[HTML_BODY_STYLE])
style = value[HTML_BODY_STYLE];
if (!style.empty())
{
TStyle styles = parseStyle(style);
TStyle::iterator it;
it = styles.find("background-repeat");
bool repeat = (it != styles.end() && it->second == "1");
// Webig only
it = styles.find("background-scale");
bool scale = (it != styles.end() && it->second == "1");
it = styles.find("background-image");
if (it != styles.end())
{
string image = it->second;
string::size_type texExt = strlwr(image).find("url(");
// Url image
if (texExt != string::npos)
// Remove url()
image = image.substr(4, image.size()-5);
setBackground (image, scale, repeat);
}
}
}
break; break;
case HTML_FORM: case HTML_FORM:
{ {
@ -1000,7 +1172,24 @@ void CGroupHTML::beginElement (uint element_number, const BOOL *present, const c
} }
else else
{ {
addImage (value[MY_HTML_IMG_SRC], globalColor); // Get the option to reload (class==reload)
bool reloadImg = false;
string style;
if (present[MY_HTML_IMG_STYLE] && value[MY_HTML_IMG_STYLE])
style = value[MY_HTML_IMG_STYLE];
if (!style.empty())
{
TStyle styles = parseStyle(style);
TStyle::iterator it;
it = styles.find("reload");
if (it != styles.end() && (*it).second == "1")
reloadImg = true;
}
addImage (value[MY_HTML_IMG_SRC], globalColor, reloadImg);
} }
} }
} }
@ -1312,8 +1501,43 @@ void CGroupHTML::beginElement (uint element_number, const BOOL *present, const c
if (!_Cells.empty()) if (!_Cells.empty())
{ {
_Cells.back() = new CGroupCell(CViewBase::TCtorParam()); _Cells.back() = new CGroupCell(CViewBase::TCtorParam());
string style;
if (present[MY_HTML_TD_STYLE] && value[MY_HTML_TD_STYLE])
style = value[MY_HTML_TD_STYLE];
// Set the cell parameters // Set the cell parameters
if (!style.empty())
{
TStyle styles = parseStyle(style);
TStyle::iterator it;
it = styles.find("background-repeat");
_Cells.back()->setTextureTile(it != styles.end());
// Webig only
it = styles.find("background-scale");
_Cells.back()->setTextureScale(it != styles.end());
it = styles.find("background-image");
if (it != styles.end())
{
nlinfo("found background-image %s", it->second.c_str());
string image = (*it).second;
string::size_type texExt = strlwr(image).find("url(");
// Url image
if (texExt != string::npos)
{
// Remove url()
image = image.substr(4, image.size()-5);
addImageDownload(image, _Cells.back());
// Image in BNP
}
else
{
_Cells.back()->setTexture(image);
}
}
}
_Cells.back()->BgColor = _CellParams.back().BgColor; _Cells.back()->BgColor = _CellParams.back().BgColor;
_Cells.back()->Align = _CellParams.back().Align; _Cells.back()->Align = _CellParams.back().Align;
_Cells.back()->VAlign = _CellParams.back().VAlign; _Cells.back()->VAlign = _CellParams.back().VAlign;
@ -1435,6 +1659,8 @@ void CGroupHTML::endElement (uint element_number)
popIfNotEmpty (_GlobalColor); popIfNotEmpty (_GlobalColor);
popIfNotEmpty (_A); popIfNotEmpty (_A);
popIfNotEmpty (_Link); popIfNotEmpty (_Link);
popIfNotEmpty (_LinkTitle);
popIfNotEmpty (_LinkClass);
break; break;
case HTML_H1: case HTML_H1:
case HTML_H2: case HTML_H2:
@ -1452,6 +1678,7 @@ void CGroupHTML::endElement (uint element_number)
break; break;
case HTML_DIV: case HTML_DIV:
_DivName = ""; _DivName = "";
popIfNotEmpty (_Divs);
break; break;
case HTML_TABLE: case HTML_TABLE:
@ -1551,7 +1778,7 @@ void CGroupHTML::endElement (uint element_number)
if (addBnpDownload(_ObjectData, _ObjectAction, _ObjectScript, _ObjectMD5Sum)) if (addBnpDownload(_ObjectData, _ObjectAction, _ObjectScript, _ObjectMD5Sum))
{ {
CInterfaceManager *pIM = CInterfaceManager::getInstance(); CInterfaceManager *pIM = CInterfaceManager::getInstance();
pIM->executeLuaScript(_ObjectScript, true); pIM->executeLuaScript("\nlocal __ALLREADYDL__=true\n"+_ObjectScript, true);
} }
_ObjectScript = ""; _ObjectScript = "";
} }
@ -1586,6 +1813,7 @@ void CGroupHTML::endUnparsedElement(const char *buffer, int length)
_ParsingLua = false; _ParsingLua = false;
// execute the embeded lua script // execute the embeded lua script
CInterfaceManager *pIM = CInterfaceManager::getInstance(); CInterfaceManager *pIM = CInterfaceManager::getInstance();
_LuaScript = "\nlocal __CURRENT_WINDOW__=\""+this->_Id+"\" \n"+_LuaScript;
pIM->executeLuaScript(_LuaScript, true); pIM->executeLuaScript(_LuaScript, true);
} }
} }
@ -2210,11 +2438,47 @@ void CGroupHTML::addString(const ucstring &str)
// Not added ? // Not added ?
if (!added) if (!added)
{
if (getA() && string(getLinkClass()) == "ryzom-ui-button")
{
string buttonTemplate = DefaultButtonGroup;
// Action handler parameters : "name=group_html_id|form=id_of_the_form|submit_button=button_name"
string param = "name=" + this->_Id + "|url=" + getLink();
CInterfaceManager *im = CInterfaceManager::getInstance();
typedef pair<string, string> TTmplParam;
vector<TTmplParam> tmplParams;
tmplParams.push_back(TTmplParam("id", ""));
tmplParams.push_back(TTmplParam("onclick", "browse"));
tmplParams.push_back(TTmplParam("onclick_param", param));
tmplParams.push_back(TTmplParam("active", "true"));
CInterfaceGroup *buttonGroup = im->createGroupInstance(buttonTemplate, _Paragraph->getId(), tmplParams);
if (buttonGroup)
{
// Add the ctrl button
CCtrlTextButton *ctrlButton = dynamic_cast<CCtrlTextButton*>(buttonGroup->getCtrl("button"));
if (!ctrlButton) ctrlButton = dynamic_cast<CCtrlTextButton*>(buttonGroup->getCtrl("b"));
if (ctrlButton)
{
ctrlButton->setModulateGlobalColorAll (false);
// Translate the tooltip
ctrlButton->setDefaultContextHelp(ucstring::makeFromUtf8(getLinkTitle()));
ctrlButton->setText(tmpStr);
}
getParagraph()->addChild (buttonGroup);
paragraphChange ();
}
}
else
{ {
CViewLink *newLink = new CViewLink(CViewBase::TCtorParam()); CViewLink *newLink = new CViewLink(CViewBase::TCtorParam());
if (getA()) if (getA())
{ {
newLink->Link = getLink(); newLink->Link = getLink();
newLink->LinkTitle = getLinkTitle();
if (!newLink->Link.empty()) if (!newLink->Link.empty())
{ {
newLink->setHTMLView (this); newLink->setHTMLView (this);
@ -2240,11 +2504,12 @@ void CGroupHTML::addString(const ucstring &str)
paragraphChange (); paragraphChange ();
} }
} }
}
} }
// *************************************************************************** // ***************************************************************************
void CGroupHTML::addImage(const char *img, bool globalColor) void CGroupHTML::addImage(const char *img, bool globalColor, bool reloadImg)
{ {
// In a paragraph ? // In a paragraph ?
if (_Paragraph) if (_Paragraph)
@ -2268,6 +2533,7 @@ void CGroupHTML::addImage(const char *img, bool globalColor)
newImage->Link = getLink(); newImage->Link = getLink();
newImage->setHTMLView (this); newImage->setHTMLView (this);
}*/ }*/
newImage->setRenderLayer(getRenderLayer()+1);
newImage->setTexture (finalUrl); newImage->setTexture (finalUrl);
newImage->setModulateGlobalColor(globalColor); newImage->setModulateGlobalColor(globalColor);
@ -2284,7 +2550,7 @@ void CGroupHTML::addImage(const char *img, bool globalColor)
// 2/ if it doesn't work, try to load the image in cache // 2/ if it doesn't work, try to load the image in cache
// //
image = localImageName(img); image = localImageName(img);
if (lookupLocalFile (finalUrl, image.c_str(), false)) if (!reloadImg && lookupLocalFile (finalUrl, image.c_str(), false))
{ {
// No more text in this text view // No more text in this text view
_CurrentViewLink = NULL; _CurrentViewLink = NULL;
@ -2314,7 +2580,9 @@ void CGroupHTML::addImage(const char *img, bool globalColor)
else*/ else*/
getParagraph()->addChild(newImage); getParagraph()->addChild(newImage);
paragraphChange (); paragraphChange ();
} else { }
else
{
// //
// 3/ if it doesn't work, display a placeholder and ask to dl the image into the cache // 3/ if it doesn't work, display a placeholder and ask to dl the image into the cache
@ -2527,6 +2795,9 @@ CCtrlButton *CGroupHTML::addButton(CCtrlButton::EType type, const std::string &/
ctrlButton->setInstantContextHelp(true); ctrlButton->setInstantContextHelp(true);
ctrlButton->setToolTipParent(TTMouse); ctrlButton->setToolTipParent(TTMouse);
ctrlButton->setToolTipParentPosRef(Hotspot_TTAuto);
ctrlButton->setToolTipPosRef(Hotspot_TTAuto);
ctrlButton->setActionOnLeftClickParams(tooltip);
} }
getParagraph()->addChild (ctrlButton); getParagraph()->addChild (ctrlButton);
@ -2556,6 +2827,7 @@ void CGroupHTML::clearContext()
_UL.clear(); _UL.clear();
_A.clear(); _A.clear();
_Link.clear(); _Link.clear();
_LinkTitle.clear();
_Tables.clear(); _Tables.clear();
_Cells.clear(); _Cells.clear();
_TR.clear(); _TR.clear();
@ -2632,6 +2904,9 @@ CInterfaceGroup *CGroupHTML::getCurrentGroup()
void CGroupHTML::addGroup (CInterfaceGroup *group, uint beginSpace) void CGroupHTML::addGroup (CInterfaceGroup *group, uint beginSpace)
{ {
if (!group)
return;
// Remove previous paragraph if empty // Remove previous paragraph if empty
if (_Paragraph && (_Paragraph->getNumChildren() == 0)) if (_Paragraph && (_Paragraph->getNumChildren() == 0))
{ {
@ -2796,7 +3071,30 @@ void CGroupHTML::setBackgroundColor (const CRGBA &bgcolor)
{ {
// Change the background color // Change the background color
bitmap->setColor (bgcolor); bitmap->setColor (bgcolor);
bitmap->setModulateGlobalColor(true); bitmap->setModulateGlobalColor(false);
}
}
}
// ***************************************************************************
void CGroupHTML::setBackground (const string &bgtex, bool scale, bool tile)
{
// Should have a child named bg
CViewBase *view = getView (DefaultBackgroundBitmapView);
if (view)
{
CViewBitmap *bitmap = dynamic_cast<CViewBitmap*> (view);
if (bitmap)
{
bitmap->setParentPosRef(Hotspot_TL);
bitmap->setPosRef(Hotspot_TL);
bitmap->setX(0);
bitmap->setY(0);
bitmap->setRenderLayer(-2);
bitmap->setScale(scale);
bitmap->setTile(tile);
addImageDownload(bgtex, view);
} }
} }
} }
@ -2897,9 +3195,6 @@ void CGroupHTML::handle ()
_Browsing = true; _Browsing = true;
updateRefreshButton(); updateRefreshButton();
// Add custom get params
addHTTPGetParams (finalUrl);
// Save new url // Save new url
_URL = finalUrl; _URL = finalUrl;
@ -2910,6 +3205,10 @@ void CGroupHTML::handle ()
initLibWWW(); initLibWWW();
_TrustedDomain = isTrustedDomain(setCurrentDomain(finalUrl)); _TrustedDomain = isTrustedDomain(setCurrentDomain(finalUrl));
// Add custom get params
addHTTPGetParams (finalUrl, _TrustedDomain);
// Get the final URL // Get the final URL
C3WSmartPtr uri = HTParse(finalUrl.c_str(), NULL, PARSE_ALL); C3WSmartPtr uri = HTParse(finalUrl.c_str(), NULL, PARSE_ALL);
@ -3030,7 +3329,7 @@ void CGroupHTML::handle ()
HTParseFormInput(formfields, (_PostFormSubmitButton + "_y=0").c_str()); HTParseFormInput(formfields, (_PostFormSubmitButton + "_y=0").c_str());
// Add custom params // Add custom params
addHTTPPostParams (formfields); addHTTPPostParams(formfields, _TrustedDomain);
// Reset the title // Reset the title
if(_TitlePrefix.empty()) if(_TitlePrefix.empty())
@ -3146,13 +3445,13 @@ void CGroupHTML::endBuild ()
// *************************************************************************** // ***************************************************************************
void CGroupHTML::addHTTPGetParams (string &/* url */) void CGroupHTML::addHTTPGetParams (string &/* url */, bool /*trustedDomain*/)
{ {
} }
// *************************************************************************** // ***************************************************************************
void CGroupHTML::addHTTPPostParams (HTAssocList * /* formfields */) void CGroupHTML::addHTTPPostParams (HTAssocList * /* formfields */, bool /*trustedDomain*/)
{ {
} }
@ -3401,7 +3700,7 @@ int CGroupHTML::luaRefresh(CLuaState &ls)
// *************************************************************************** // ***************************************************************************
int CGroupHTML::luaRemoveContent(CLuaState &ls) int CGroupHTML::luaRemoveContent(CLuaState &ls)
{ {
const char *funcName = "refresh"; const char *funcName = "removeContent";
CLuaIHM::checkArgCount(ls, funcName, 0); CLuaIHM::checkArgCount(ls, funcName, 0);
removeContent(); removeContent();
return 0; return 0;

@ -30,6 +30,8 @@
#include "ctrl_button.h" #include "ctrl_button.h"
#include "group_table.h" #include "group_table.h"
typedef std::map<std::string, std::string> TStyle;
extern "C" extern "C"
{ {
#include "WWWInit.h" #include "WWWInit.h"
@ -147,6 +149,7 @@ public:
std::string DefaultCheckBoxBitmapPushed; std::string DefaultCheckBoxBitmapPushed;
std::string DefaultCheckBoxBitmapOver; std::string DefaultCheckBoxBitmapOver;
std::string DefaultBackgroundBitmapView; std::string DefaultBackgroundBitmapView;
std::string CurrentLinkTitle;
// Browser home // Browser home
std::string Home; std::string Home;
@ -216,10 +219,10 @@ protected :
virtual void endUnparsedElement(const char *buffer, int length); virtual void endUnparsedElement(const char *buffer, int length);
// Add GET params to the url // Add GET params to the url
virtual void addHTTPGetParams (std::string &url); virtual void addHTTPGetParams (std::string &url, bool trustedDomain);
// Add POST params to the libwww list // Add POST params to the libwww list
virtual void addHTTPPostParams (HTAssocList *formfields); virtual void addHTTPPostParams (HTAssocList *formfields, bool trustedDomain);
// the current request is terminated // the current request is terminated
virtual void requestTerminated(HTRequest *request); virtual void requestTerminated(HTRequest *request);
@ -227,6 +230,9 @@ protected :
// Get Home URL // Get Home URL
virtual std::string home(); virtual std::string home();
// Parse style html tag
TStyle parseStyle(const std::string &str_styles);
// Handle some work at each pass // Handle some work at each pass
virtual void handle (); virtual void handle ();
@ -251,7 +257,7 @@ protected :
void addString(const ucstring &str); void addString(const ucstring &str);
// Add an image in the current paragraph // Add an image in the current paragraph
void addImage(const char *image, bool globalColor); void addImage(const char *image, bool globalColor, bool reloadImg=false);
// Add a text area in the current paragraph // Add a text area in the current paragraph
CInterfaceGroup *addTextArea (const std::string &templateName, const char *name, uint rows, uint cols, bool multiLine, const ucstring &content); CInterfaceGroup *addTextArea (const std::string &templateName, const char *name, uint rows, uint cols, bool multiLine, const ucstring &content);
@ -266,6 +272,9 @@ protected :
// Set the background color // Set the background color
void setBackgroundColor (const NLMISC::CRGBA &bgcolor); void setBackgroundColor (const NLMISC::CRGBA &bgcolor);
// Set the background
void setBackground (const std::string &bgtex, bool scale, bool tile);
// Force the current string to be in a single string // Force the current string to be in a single string
void flushString(); void flushString();
@ -397,6 +406,30 @@ protected :
return _Link.back().c_str(); return _Link.back().c_str();
} }
std::vector<std::string> _LinkTitle;
inline const char *getLinkTitle() const
{
if (_LinkTitle.empty())
return "";
return _LinkTitle.back().c_str();
}
std::vector<std::string> _LinkClass;
inline const char *getLinkClass() const
{
if (_LinkClass.empty())
return "";
return _LinkClass.back().c_str();
}
// Divs (i.e. interface group)
std::vector<class CInterfaceGroup*> _Divs;
inline CInterfaceGroup *getDiv() const
{
if (_Divs.empty())
return NULL;
return _Divs.back();
}
// Tables // Tables
std::vector<class CGroupTable*> _Tables; std::vector<class CGroupTable*> _Tables;
inline CGroupTable *getTable() const inline CGroupTable *getTable() const
@ -475,6 +508,7 @@ protected :
NoWrap = false; NoWrap = false;
} }
NLMISC::CRGBA BgColor; NLMISC::CRGBA BgColor;
std::string Style;
CGroupCell::TAlign Align; CGroupCell::TAlign Align;
CGroupCell::TVAlign VAlign; CGroupCell::TVAlign VAlign;
sint32 LeftMargin; sint32 LeftMargin;
@ -582,9 +616,9 @@ private:
void checkImageDownload(); void checkImageDownload();
void addImageDownload(const std::string &url, CViewBase *img); void addImageDownload(const std::string &url, CViewBase *img);
std::string localImageName(const std::string &url); std::string localImageName(const std::string &url);
bool isTrustedDomain(const std::string &domain);
bool isTrustedDomain(const std::string &domain);
void setImage(CViewBase *view, const std::string &file);
// BnpDownload system // BnpDownload system
void initBnpDownload(); void initBnpDownload();

@ -24,6 +24,7 @@
#include "group_html_cs.h" #include "group_html_cs.h"
#include "game_share/xml_auto_ptr.h" #include "game_share/xml_auto_ptr.h"
#include "../client_cfg.h" #include "../client_cfg.h"
#include "interface_manager.h"
// used for login cookie to be sent to the web server // used for login cookie to be sent to the web server
#include "../net_manager.h" #include "../net_manager.h"
@ -49,7 +50,7 @@ CGroupHTMLCS::~CGroupHTMLCS()
// *************************************************************************** // ***************************************************************************
void CGroupHTMLCS::addHTTPGetParams (string &url) void CGroupHTMLCS::addHTTPGetParams (string &url, bool /*trustedDomain*/)
{ {
url += ((url.find('?') != string::npos) ? "&" : "?"); url += ((url.find('?') != string::npos) ? "&" : "?");
@ -69,7 +70,7 @@ void CGroupHTMLCS::addHTTPGetParams (string &url)
// *************************************************************************** // ***************************************************************************
void CGroupHTMLCS::addHTTPPostParams (HTAssocList *formfields) void CGroupHTMLCS::addHTTPPostParams (HTAssocList *formfields, bool /*trustedDomain*/)
{ {
std::vector<CParameter> parameters; std::vector<CParameter> parameters;
getParameters (parameters, false); getParameters (parameters, false);
@ -120,6 +121,15 @@ void CGroupHTMLCS::getParameters (std::vector<CParameter> &parameters, bool enco
string s = getDebugInformation(); string s = getDebugInformation();
s += getSystemInformation(); s += getSystemInformation();
static bool webIgReady = false;
if (!webIgReady) // Webig is ready when getParameters of CGroupHTMLCS is called
{
webIgReady = true;
CInterfaceManager *pIM = CInterfaceManager::getInstance();
pIM->executeLuaScript("game:onWebIgReady()");
}
// For each line // For each line
string::size_type startOfLine = 0; string::size_type startOfLine = 0;
string::size_type endOfLine; string::size_type endOfLine;

@ -39,8 +39,8 @@ public:
~CGroupHTMLCS(); ~CGroupHTMLCS();
// From CGroupHTML // From CGroupHTML
virtual void addHTTPGetParams (std::string &url); virtual void addHTTPGetParams (std::string &url, bool trustedDomain);
virtual void addHTTPPostParams (HTAssocList *formfields); virtual void addHTTPPostParams (HTAssocList *formfields, bool trustedDomain);
virtual std::string home(); virtual std::string home();
private: private:

@ -51,9 +51,9 @@ CGroupHTMLForum::~CGroupHTMLForum()
// *************************************************************************** // ***************************************************************************
void CGroupHTMLForum::addHTTPGetParams (string &url) void CGroupHTMLForum::addHTTPGetParams (string &url, bool /*trustedDomain*/)
{ {
ucstring user_name = UserEntity->getDisplayName (); ucstring user_name = UserEntity->getLoginName ();
const SGuild &guild = CGuildManager::getInstance()->getGuild(); const SGuild &guild = CGuildManager::getInstance()->getGuild();
string gname = guild.Name.toUtf8(); string gname = guild.Name.toUtf8();
@ -83,9 +83,9 @@ void CGroupHTMLForum::addHTTPGetParams (string &url)
// *************************************************************************** // ***************************************************************************
void CGroupHTMLForum::addHTTPPostParams (HTAssocList *formfields) void CGroupHTMLForum::addHTTPPostParams (HTAssocList *formfields, bool /*trustedDomain*/)
{ {
ucstring user_name = UserEntity->getDisplayName (); ucstring user_name = UserEntity->getLoginName ();
const SGuild &guild = CGuildManager::getInstance()->getGuild(); const SGuild &guild = CGuildManager::getInstance()->getGuild();
string gname = guild.Name.toUtf8(); string gname = guild.Name.toUtf8();
@ -115,12 +115,13 @@ string CGroupHTMLForum::home ()
void CGroupHTMLForum::handle () void CGroupHTMLForum::handle ()
{ {
// Do nothing if WebServer is not initialized /* // Do nothing if WebServer is not initialized
if (!WebServer.empty()) if (!WebServer.empty())
{ {
Home = WebServer+"forum.php"; Home = WebServer+"forum.php";
CGroupHTML::handle (); CGroupHTML::handle ();
} }
*/
} }
// *************************************************************************** // ***************************************************************************

@ -39,8 +39,8 @@ public:
~CGroupHTMLForum(); ~CGroupHTMLForum();
// From CGroupHTML // From CGroupHTML
virtual void addHTTPGetParams (std::string &url); virtual void addHTTPGetParams (std::string &url, bool trustedDomain);
virtual void addHTTPPostParams (HTAssocList *formfields); virtual void addHTTPPostParams (HTAssocList *formfields, bool trustedDomain);
virtual std::string home(); virtual std::string home();
virtual void handle (); virtual void handle ();

@ -50,9 +50,9 @@ CGroupHTMLMail::~CGroupHTMLMail()
// *************************************************************************** // ***************************************************************************
void CGroupHTMLMail::addHTTPGetParams (string &url) void CGroupHTMLMail::addHTTPGetParams (string &url, bool /*trustedDomain*/)
{ {
ucstring user_name = UserEntity->getDisplayName (); ucstring user_name = UserEntity->getLoginName ();
url += ((url.find('?') != string::npos) ? "&" : "?") + url += ((url.find('?') != string::npos) ? "&" : "?") +
string("shard=") + toString(CharacterHomeSessionId) + string("shard=") + toString(CharacterHomeSessionId) +
string("&user_login=") + user_name.toString() + string("&user_login=") + user_name.toString() +
@ -62,9 +62,9 @@ void CGroupHTMLMail::addHTTPGetParams (string &url)
// *************************************************************************** // ***************************************************************************
void CGroupHTMLMail::addHTTPPostParams (HTAssocList *formfields) void CGroupHTMLMail::addHTTPPostParams (HTAssocList *formfields, bool /*trustedDomain*/)
{ {
ucstring user_name = UserEntity->getDisplayName (); ucstring user_name = UserEntity->getLoginName ();
HTParseFormInput(formfields, ("shard="+toString(CharacterHomeSessionId)).c_str()); HTParseFormInput(formfields, ("shard="+toString(CharacterHomeSessionId)).c_str());
HTParseFormInput(formfields, ("user_login="+user_name.toString()).c_str()); HTParseFormInput(formfields, ("user_login="+user_name.toString()).c_str());
HTParseFormInput(formfields, ("session_cookie="+NetMngr.getLoginCookie().toString()).c_str()); HTParseFormInput(formfields, ("session_cookie="+NetMngr.getLoginCookie().toString()).c_str());
@ -85,11 +85,12 @@ string CGroupHTMLMail::home ()
void CGroupHTMLMail::handle () void CGroupHTMLMail::handle ()
{ {
// Do nothing if WebServer is not initialized // Do nothing if WebServer is not initialized
if (!WebServer.empty()) /* if (!WebServer.empty())
{ {
Home = WebServer+"mailbox.php"; Home = WebServer+"mailbox.php";
CGroupHTML::handle (); CGroupHTML::handle ();
} }
*/
} }
// *************************************************************************** // ***************************************************************************

@ -39,8 +39,8 @@ public:
~CGroupHTMLMail(); ~CGroupHTMLMail();
// From CGroupHTML // From CGroupHTML
virtual void addHTTPGetParams (std::string &url); virtual void addHTTPGetParams (std::string &url, bool trustedDomain);
virtual void addHTTPPostParams (HTAssocList *formfields); virtual void addHTTPPostParams (HTAssocList *formfields, bool trustedDomain);
virtual std::string home(); virtual std::string home();
virtual void handle (); virtual void handle ();

@ -20,6 +20,7 @@
#include "game_share/xml_auto_ptr.h" #include "game_share/xml_auto_ptr.h"
#include "../client_cfg.h" #include "../client_cfg.h"
#include "../user_entity.h" #include "../user_entity.h"
#include "../entities.h"
#include "interface_manager.h" #include "interface_manager.h"
// used for login cookie to be sent to the web server // used for login cookie to be sent to the web server
@ -55,7 +56,7 @@ static string getWebAuthKey()
// authkey = <sharid><name><cid><cookie> // authkey = <sharid><name><cid><cookie>
uint32 cid = NetMngr.getLoginCookie().getUserId() * 16 + PlayerSelectedSlot; uint32 cid = NetMngr.getLoginCookie().getUserId() * 16 + PlayerSelectedSlot;
string rawKey = toString(CharacterHomeSessionId) + string rawKey = toString(CharacterHomeSessionId) +
UserEntity->getDisplayName().toString() + UserEntity->getLoginName().toString() +
toString(cid) + toString(cid) +
NetMngr.getLoginCookie().toString(); NetMngr.getLoginCookie().toString();
string key = getMD5((const uint8*)rawKey.c_str(), (uint32)rawKey.size()).toString(); string key = getMD5((const uint8*)rawKey.c_str(), (uint32)rawKey.size()).toString();
@ -64,18 +65,72 @@ static string getWebAuthKey()
return key; return key;
} }
void addWebIGParams (string &url) void addWebIGParams (string &url, bool trustedDomain)
{ {
if(!UserEntity || !NetMngr.getLoginCookie().isValid()) return; if(!UserEntity || !NetMngr.getLoginCookie().isValid()) return;
uint32 cid = NetMngr.getLoginCookie().getUserId() * 16 + PlayerSelectedSlot; uint32 cid = NetMngr.getLoginCookie().getUserId() * 16 + PlayerSelectedSlot;
url += ((url.find('?') != string::npos) ? "&" : "?") + url += ((url.find('?') != string::npos) ? "&" : "?") +
string("shardid=") + toString(CharacterHomeSessionId) + string("shardid=") + toString(CharacterHomeSessionId) +
string("&name=") + UserEntity->getDisplayName().toUtf8() + string("&name=") + UserEntity->getLoginName().toUtf8() +
string("&cid=") + toString(cid) + string("&lang=") + CI18N::getCurrentLanguageCode() +
string("&authkey=") + getWebAuthKey() + string("&ig=1");
string("&ig=1") + if (trustedDomain)
string("&lang=") + CI18N::getCurrentLanguageCode(); {
url += string("&cid=") + toString(cid) +
string("&authkey=") + getWebAuthKey();
if (url.find('$') != string::npos)
{
strFindReplace(url, "$datasetid$", toString(UserEntity->dataSetId()));
strFindReplace(url, "$gender$", GSGENDER::toString(UserEntity->getGender()));
strFindReplace(url, "$displayName$", UserEntity->getDisplayName().toString());
strFindReplace(url, "$posx$", toString(UserEntity->pos().x));
strFindReplace(url, "$posy$", toString(UserEntity->pos().y));
strFindReplace(url, "$posz$", toString(UserEntity->pos().z));
strFindReplace(url, "$post$", toString(atan2(UserEntity->front().y, UserEntity->front().x)));
// Target fields
const char *dbPath = "UI:VARIABLES:TARGET:SLOT";
CInterfaceManager *im = CInterfaceManager::getInstance();
CCDBNodeLeaf *node = im->getDbProp(dbPath, false);
if (node && (uint8)node->getValue32() != (uint8) CLFECOMMON::INVALID_SLOT)
{
CEntityCL *target = EntitiesMngr.entity((uint) node->getValue32());
if (target)
{
strFindReplace(url, "$tdatasetid$", toString(target->dataSetId()));
strFindReplace(url, "$tdisplayName$", target->getDisplayName().toString());
strFindReplace(url, "$tposx$", toString(target->pos().x));
strFindReplace(url, "$tposy$", toString(target->pos().y));
strFindReplace(url, "$tposz$", toString(target->pos().z));
strFindReplace(url, "$tpost$", toString(atan2(target->front().y, target->front().x)));
strFindReplace(url, "$tsheet$", target->sheetId().toString());
string type;
if (target->isFauna())
type = "fauna";
else if (target->isNPC())
type = "npc";
else if (target->isPlayer())
type = "player";
else if (target->isUser())
type = "user";
strFindReplace(url, "$ttype$", target->sheetId().toString());
}
else
{
strFindReplace(url, "$tdatasetid$", "");
strFindReplace(url, "$tdisplayName$", "");
strFindReplace(url, "$tposx$", "");
strFindReplace(url, "$tposy$", "");
strFindReplace(url, "$tposz$", "");
strFindReplace(url, "$tpost$", "");
strFindReplace(url, "$tsheet$", "");
strFindReplace(url, "$ttype$", "");
}
}
}
}
} }
// *************************************************************************** // ***************************************************************************
@ -204,7 +259,7 @@ struct CWebigNotificationThread : public NLMISC::IRunnable
while (true) while (true)
{ {
string url = "http://"+ClientCfg.WebIgMainDomain+"/start/index.php?app=notif&rnd="+randomString(); string url = "http://"+ClientCfg.WebIgMainDomain+"/start/index.php?app=notif&rnd="+randomString();
addWebIGParams(url); addWebIGParams(url, true);
get(url); get(url);
nlSleep(10*60*1000); nlSleep(10*60*1000);
} }
@ -231,53 +286,100 @@ void startWebigNotificationThread()
// *************************************************************************** // ***************************************************************************
NLMISC_REGISTER_OBJECT(CViewBase, CGroupHTMLWebIG, std::string, "webig_html"); NLMISC_REGISTER_OBJECT(CViewBase, CGroupHTMLAuth, std::string, "auth_html");
CGroupHTMLWebIG::CGroupHTMLWebIG(const TCtorParam &param) CGroupHTMLAuth::CGroupHTMLAuth(const TCtorParam &param)
: CGroupHTML(param) : CGroupHTML(param)
{ {
startWebigNotificationThread();
} }
// *************************************************************************** // ***************************************************************************
CGroupHTMLWebIG::~CGroupHTMLWebIG() CGroupHTMLAuth::~CGroupHTMLAuth()
{ {
} }
void CGroupHTMLWebIG::addHTTPGetParams (string &url) void CGroupHTMLAuth::addHTTPGetParams (string &url, bool trustedDomain)
{ {
addWebIGParams(url); addWebIGParams(url, trustedDomain);
} }
// *************************************************************************** // ***************************************************************************
void CGroupHTMLWebIG::addHTTPPostParams (HTAssocList *formfields) void CGroupHTMLAuth::addHTTPPostParams (HTAssocList *formfields, bool trustedDomain)
{ {
if(!UserEntity) return; if(!UserEntity) return;
uint32 cid = NetMngr.getLoginCookie().getUserId() * 16 + PlayerSelectedSlot; uint32 cid = NetMngr.getLoginCookie().getUserId() * 16 + PlayerSelectedSlot;
HTParseFormInput(formfields, ("shardid="+toString(CharacterHomeSessionId)).c_str()); HTParseFormInput(formfields, ("shardid="+toString(CharacterHomeSessionId)).c_str());
HTParseFormInput(formfields, ("name="+UserEntity->getDisplayName().toUtf8()).c_str()); HTParseFormInput(formfields, ("name="+UserEntity->getLoginName().toUtf8()).c_str());
HTParseFormInput(formfields, ("lang="+CI18N::getCurrentLanguageCode()).c_str());
HTParseFormInput(formfields, "ig=1");
if (trustedDomain)
{
HTParseFormInput(formfields, ("cid="+toString(cid)).c_str()); HTParseFormInput(formfields, ("cid="+toString(cid)).c_str());
HTParseFormInput(formfields, ("authkey="+getWebAuthKey()).c_str()); HTParseFormInput(formfields, ("authkey="+getWebAuthKey()).c_str());
HTParseFormInput(formfields, "ig=1"); }
HTParseFormInput(formfields, ("lang="+CI18N::getCurrentLanguageCode()).c_str());
} }
// *************************************************************************** // ***************************************************************************
string CGroupHTMLWebIG::home () string CGroupHTMLAuth::home ()
{ {
return Home; return Home;
} }
// *************************************************************************** // ***************************************************************************
void CGroupHTMLWebIG::handle () void CGroupHTMLAuth::handle ()
{ {
// Home = "http://atys.ryzom.com/start/index.php";
CGroupHTML::handle (); CGroupHTML::handle ();
} }
// *************************************************************************** // ***************************************************************************
// ***************************************************************************
// ***************************************************************************
NLMISC_REGISTER_OBJECT(CViewBase, CGroupHTMLWebIG, std::string, "webig_html");
CGroupHTMLWebIG::CGroupHTMLWebIG(const TCtorParam &param)
: CGroupHTMLAuth(param)
{
startWebigNotificationThread();
}
// ***************************************************************************
CGroupHTMLWebIG::~CGroupHTMLWebIG()
{
}
// ***************************************************************************
void CGroupHTMLWebIG::addHTTPGetParams (string &url, bool trustedDomain)
{
CGroupHTMLAuth::addHTTPGetParams(url, trustedDomain);
}
// ***************************************************************************
void CGroupHTMLWebIG::addHTTPPostParams (HTAssocList *formfields, bool trustedDomain)
{
CGroupHTMLAuth::addHTTPPostParams(formfields, trustedDomain);
}
// ***************************************************************************
string CGroupHTMLWebIG::home ()
{
return Home;
}
// ***************************************************************************
void CGroupHTMLWebIG::handle ()
{
CGroupHTMLAuth::handle ();
}

@ -20,10 +20,32 @@
#include "nel/misc/types_nl.h" #include "nel/misc/types_nl.h"
#include "group_html.h" #include "group_html.h"
/**
* Auth HTML group
*/
class CGroupHTMLAuth : public CGroupHTML
{
public:
// Constructor
CGroupHTMLAuth(const TCtorParam &param);
~CGroupHTMLAuth();
// From CGroupHTML
virtual void addHTTPGetParams (std::string &url, bool trustedDomain);
virtual void addHTTPPostParams (HTAssocList *formfields, bool trustedDomain);
virtual std::string home();
virtual void handle ();
private:
};
/** /**
* WebIG HTML group * WebIG HTML group
*/ */
class CGroupHTMLWebIG : public CGroupHTML class CGroupHTMLWebIG : public CGroupHTMLAuth
{ {
public: public:
@ -31,9 +53,9 @@ public:
CGroupHTMLWebIG(const TCtorParam &param); CGroupHTMLWebIG(const TCtorParam &param);
~CGroupHTMLWebIG(); ~CGroupHTMLWebIG();
// From CGroupHTML /// From CGroupHTMLAuth
virtual void addHTTPGetParams (std::string &url); virtual void addHTTPGetParams (std::string &url, bool trustedDomain);
virtual void addHTTPPostParams (HTAssocList *formfields); virtual void addHTTPPostParams (HTAssocList *formfields, bool trustedDomain);
virtual std::string home(); virtual std::string home();
virtual void handle (); virtual void handle ();

@ -973,6 +973,132 @@ void CGroupInSceneBubbleManager::dynChatOpen (uint32 nBotUID, uint32 nBotName, c
UserEntity->interlocutor( pChar->slot() ); UserEntity->interlocutor( pChar->slot() );
} }
// ***************************************************************************
void CGroupInSceneBubbleManager::webIgChatOpen (uint32 nBotUID, string text, const vector<string> &strs, const vector<string> &links)
{
CInterfaceManager *pIM = CInterfaceManager::getInstance();
// If the character doesn't exist in view field -> do not display the bubble
CEntityCL *pEntity = EntitiesMngr.getEntityByCompressedIndex(nBotUID);
CCharacterCL *pChar = dynamic_cast<CCharacterCL*>(pEntity);
if (pChar == NULL)
{
nlwarning("character probably too far");
return;
}
// Look if we get a bubble with this nBotUID ?
uint32 pos, j;
for (pos = 0; pos < _DynBubbles.size(); ++pos)
{
if (_DynBubbles[pos].BotUID == nBotUID)
break;
}
// If the bubble doesn't exist -> create
CGroupInSceneBubble *bubble = NULL;
string id;
if (pos == _DynBubbles.size())
{
uint32 i = 0;
while (getDynBubble(i) != NULL) i++;
id = "in_scene_webig_bubble_" + toString(i);
// Create the instance
std::vector<std::pair<std::string,std::string> > templateParams;
templateParams.push_back (std::pair<std::string,std::string>("id", id));
CInterfaceGroup *group = pIM->createGroupInstance ("webig_3dbulle_L", "ui:interface", templateParams);
if (group == NULL)
{
nlwarning("cannot create webig_3dbulle_L");
return;
}
// Link to the interface
pIM->addWindowToMasterGroup("ui:interface", group);
CInterfaceGroup *pRoot = dynamic_cast<CInterfaceGroup*>(pIM->getElementFromId("ui:interface"));
group->setParent(pRoot);
if (pRoot)
pRoot->addGroup (group);
group->setActive(false);
bubble = dynamic_cast<CGroupInSceneBubble*>(group);
if (bubble == NULL)
{
nlwarning("cannot cast to CGroupInSceneBubble");
return;
}
CDynBubble dynBubble;
dynBubble.BotName = 0;
dynBubble.BotUID = nBotUID;
dynBubble.Bubble = bubble;
_DynBubbles.push_back(dynBubble);
}
else
{
bubble = _DynBubbles[pos].Bubble;
// Remove from group to delete if in the same frame
for (j=0; j<_GroupToDelete.size(); j++)
if (_GroupToDelete[j] == bubble)
{
_GroupToDelete.erase(_GroupToDelete.begin()+j);
break;
}
}
// Update the bubble's texts
ucstring ucText;
ucText.fromUtf8(text);
bubble->setText(ucText);
id = bubble->getId() + ":header_opened:window:";
CViewText *pVT;
CCtrlLink *pCL;
_DynBubbles[pos].DescWaiting = 0;
for (j = 0; j < 8; ++j)
{
pVT = dynamic_cast<CViewText*>(bubble->getElement(id+"opt"+toString(j)));
if (pVT != NULL)
{
pVT->setActive(false);
pVT->setText(ucstring(""));
}
pCL = dynamic_cast<CCtrlLink*>(bubble->getElement(id+"optb"+toString(j)));
if (pCL != NULL) pCL->setActive(false);
}
for (j = 0; j < strs.size(); ++j)
{
string fullid = id+"opt"+toString(j);
pVT = dynamic_cast<CViewText*>(bubble->getElement(id+"opt"+toString(j)));
if (pVT != NULL)
{
pVT->setActive(true);
ucstring optionText;
optionText.fromUtf8(strs[j]);
pVT->setText(optionText);
pCL = dynamic_cast<CCtrlLink*>(bubble->getElement(id+"optb"+toString(j)));
if (pCL != NULL)
{
pCL->setActionOnLeftClick("browse");
pCL->setParamsOnLeftClick("name=ui:interface:web_transactions:content:html|show=0|url="+links[j]);
//pCL->setActionOnLeftClickParams("name=ui:interface:web_transactions:content:html|url="+links[j]);
pCL->setActive(true);
}
}
}
// Link bubble to the character
pChar->setBubble(bubble);
// Make the npc face the character
UserEntity->interlocutor( pChar->slot() );
}
uint32 CGroupInSceneBubbleManager::CDynBubble::getOptionStringId(uint option) uint32 CGroupInSceneBubbleManager::CDynBubble::getOptionStringId(uint option)
{ {
if (!Bubble) return 0; if (!Bubble) return 0;

@ -64,6 +64,9 @@ public:
// Open a Dynamic Chat // Open a Dynamic Chat
void dynChatOpen (uint32 nBotUID, uint32 nBotName, const std::vector<uint32> &DynStrs); void dynChatOpen (uint32 nBotUID, uint32 nBotName, const std::vector<uint32> &DynStrs);
// Open a Dynamic Chat from webig
void webIgChatOpen (uint32 nBotUID, std::string sBotName, const std::vector<std::string> &strs, const std::vector<std::string> &links);
// Close a Dynamic Chat // Close a Dynamic Chat
void dynChatClose (uint32 nBotUID); void dynChatClose (uint32 nBotUID);

@ -97,7 +97,7 @@ CRGBA CGroupInSceneUserInfo::BarColorHPNegative = CRGBA(127, 32, 0);
#define nlfsinfo2 if ( _Entity->isForageSource() ) nlinfo #define nlfsinfo2 if ( _Entity->isForageSource() ) nlinfo
CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity) CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (CEntityCL *entity)
{ {
// Get the interface manager // Get the interface manager
CInterfaceManager *pIM = CInterfaceManager::getInstance(); CInterfaceManager *pIM = CInterfaceManager::getInstance();
@ -129,6 +129,7 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
bool forageSourceBarDisplayed= false; bool forageSourceBarDisplayed= false;
bool needPvPLogo= false; bool needPvPLogo= false;
bool permanentContent = false; bool permanentContent = false;
bool rpTags = false;
bool displayMissionIcons = pIM->getDbProp("UI:SAVE:INSCENE:FRIEND:MISSION_ICON")->getValueBool(); bool displayMissionIcons = pIM->getDbProp("UI:SAVE:INSCENE:FRIEND:MISSION_ICON")->getValueBool();
// Names // Names
@ -136,6 +137,12 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
ucstring theTribeName; ucstring theTribeName;
ucstring entityName = entity->getDisplayName(); ucstring entityName = entity->getDisplayName();
ucstring entityTitle = entity->getTitle(); ucstring entityTitle = entity->getTitle();
ucstring entityTag1 = entity->getTag(1);
ucstring entityTag2 = entity->getTag(2);
ucstring entityTag3 = entity->getTag(3);
ucstring entityTag4 = entity->getTag(4);
string entityPermanentContent = entity->getPermanentStatutIcon(); string entityPermanentContent = entity->getPermanentStatutIcon();
// Active fields and bars // Active fields and bars
@ -160,6 +167,8 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
} }
else if(npcFriendAndNeutral) else if(npcFriendAndNeutral)
{ {
string dbEntry;
getBarSettings( pIM, user, entity->isPlayer(), _friend, dbEntry, bars );
// For RoleMasters, merchants etc... must display name and function, and nothing else // For RoleMasters, merchants etc... must display name and function, and nothing else
for(uint i=0;i<NumBars;i++) for(uint i=0;i<NumBars;i++)
bars[i]= false; bars[i]= false;
@ -168,6 +177,7 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
title= true; title= true;
guildName= false; guildName= false;
templateName = "in_scene_user_info"; templateName = "in_scene_user_info";
rpTags = (!entityTag1.empty() || !entityTag2.empty() || !entityTag3.empty() || !entityTag4.empty() ) && pIM->getDbProp(dbEntry+"RPTAGS")->getValueBool();
} }
else else
{ {
@ -176,6 +186,7 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
getBarSettings( pIM, user, entity->isPlayer(), _friend, dbEntry, bars ); getBarSettings( pIM, user, entity->isPlayer(), _friend, dbEntry, bars );
name = !entityName.empty() && pIM->getDbProp(dbEntry+"NAME")->getValueBool(); name = !entityName.empty() && pIM->getDbProp(dbEntry+"NAME")->getValueBool();
title = !entityTitle.empty() && pIM->getDbProp(dbEntry+"TITLE")->getValueBool(); title = !entityTitle.empty() && pIM->getDbProp(dbEntry+"TITLE")->getValueBool();
rpTags = (!entityTag1.empty() || !entityTag2.empty() || !entityTag3.empty() || !entityTag4.empty() ) && pIM->getDbProp(dbEntry+"RPTAGS")->getValueBool();
// if name is empty but not title, title is displayed as name // if name is empty but not title, title is displayed as name
if (!title && entityName.empty() && !entityTitle.empty() && pIM->getDbProp(dbEntry+"NAME")->getValueBool()) if (!title && entityName.empty() && !entityTitle.empty() && pIM->getDbProp(dbEntry+"NAME")->getValueBool())
title = true; title = true;
@ -369,6 +380,26 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
else else
stringSpace += textH; stringSpace += textH;
if (rpTags)
{
CPlayerCL * pPlayer = dynamic_cast<CPlayerCL*>(entity);
CViewBitmap *bitmap;
if (pPlayer == NULL || (pPlayer != NULL && pPlayer->getPvpMode() & PVP_MODE::PvpFaction))
{
bitmap = dynamic_cast<CViewBitmap*>(leftGroup->getView ("rp_logo_1"));
if (bitmap)
bitmap->setTexture(entityTag1.toString());
bitmap = dynamic_cast<CViewBitmap*>(leftGroup->getView ("rp_logo_2"));
if (bitmap)
bitmap->setTexture(entityTag2.toString());
}
bitmap = dynamic_cast<CViewBitmap*>(leftGroup->getView ("rp_logo_3"));
if (bitmap)
bitmap->setTexture(entityTag3.toString());
bitmap = dynamic_cast<CViewBitmap*>(leftGroup->getView ("rp_logo_4"));
if (bitmap)
bitmap->setTexture(entityTag4.toString());
}
// Get the permanent content bitmap // Get the permanent content bitmap
if(permanentContent) if(permanentContent)
@ -539,162 +570,96 @@ CGroupInSceneUserInfo *CGroupInSceneUserInfo::build (class CEntityCL *entity)
info->_MissionTarget = bitmap; info->_MissionTarget = bitmap;
} }
CViewBase * pvpCivLogo = info->getView ("pvp_faction_civ_logo"); CViewBase * pvpFactionLogo = info->getView ("pvp_faction_logo");
CViewBase * pvpCultLogo = info->getView ("pvp_faction_cult_logo"); CViewBase * pvpOutpostLogo = info->getView ("pvp_outpost_logo");
CViewBase * pvpDuelLogo = info->getView ("pvp_duel_logo");
CPlayerCL * pPlayer = dynamic_cast<CPlayerCL*>(entity); CPlayerCL * pPlayer = dynamic_cast<CPlayerCL*>(entity);
if (pPlayer == NULL) if (pPlayer == NULL)
needPvPLogo = false; needPvPLogo = false;
// set or inactive pvp logos
bool needCivPvpLogo = needPvPLogo;
bool needCultPvpLogo = needPvPLogo;
if (pPlayer != NULL && needPvPLogo && pvpCivLogo && pvpCultLogo) if (pPlayer != NULL && needPvPLogo)
{ {
uint8 civToDisplay = (uint8)(pPlayer->getClanCivMaxFame() & 0xFF); if (pvpFactionLogo)
uint8 cultToDisplay = (uint8)(pPlayer->getClanCultMaxFame() & 0xFF);
if (!entity->isUser())
{ {
bool civEnnemies = false; pvpFactionLogo->setActive(true);
for (uint8 i = 0; i < 4; i++) CViewBitmap * pvpFactionBitmap = dynamic_cast<CViewBitmap *>(pvpFactionLogo);
if( pvpFactionBitmap )
{ {
if ( (pPlayer->isPvpAlly(i) && UserEntity->isPvpEnnemy(i)) || if (user)
(pPlayer->isPvpEnnemy(i) && UserEntity->isPvpAlly(i)) )
{ {
civEnnemies = true; if (pPlayer->getPvpMode() & PVP_MODE::PvpChallenge)
if ( civToDisplay == i)
break;
else
civToDisplay = i;
}
if (!civEnnemies)
{ {
if ( (pPlayer->isPvpAlly(i) && UserEntity->isPvpAlly(i)) || pvpFactionBitmap->setTexture("ico_curse.tga");
(pPlayer->isPvpEnnemy(i) && UserEntity->isPvpEnnemy(i)) )
{
if ( civToDisplay == i)
break;
else
civToDisplay = i;
} }
} else if (pPlayer->getPvpMode() & PVP_MODE::PvpFaction)
}
for (uint8 i = 4; i < 7; i++)
{ {
if ( (pPlayer->isPvpAlly(i) && UserEntity->isPvpEnnemy(i)) || if (pPlayer->getPvpMode() & PVP_MODE::PvpZoneSafe)
(pPlayer->isPvpEnnemy(i) && UserEntity->isPvpAlly(i)) ) pvpFactionBitmap->setTexture("pvp_neutral.tga");
{
if ( cultToDisplay == i)
break;
else else
cultToDisplay = i; pvpFactionBitmap->setTexture("pvp_enemy_tag.tga");
} }
else if (pPlayer->getPvpMode() & PVP_MODE::PvpFactionFlagged)
if ( (pPlayer->isPvpAlly(i) && UserEntity->isPvpAlly(i)) ||
(pPlayer->isPvpEnnemy(i) && UserEntity->isPvpEnnemy(i)) )
{ {
if ( cultToDisplay == i) if (pPlayer->getPvpMode() & PVP_MODE::PvpSafe)
break; pvpFactionBitmap->setTexture("pvp_neutral.tga");
else else
cultToDisplay = i; pvpFactionBitmap->setTexture("pvp_enemy_flag.tga");
}
}
} }
if ((pPlayer->getPvpMode() & PVP_MODE::PvpFaction) || (pPlayer->getPvpMode() & PVP_MODE::PvpFactionFlagged))
{
CViewBitmap * pvpCivLogoBmp = dynamic_cast<CViewBitmap *>(pvpCivLogo);
if( pvpCivLogoBmp )
{
if (pPlayer->isPvpAlly(civToDisplay))
{
if (pPlayer->isPvpRanger())
pvpCivLogoBmp->setTexture("pvp_ally_ranger.tga");
else else
pvpCivLogoBmp->setTexture("pvp_ally_"+toString(civToDisplay)+".tga"); pvpFactionLogo->setActive(false);
} }
else if (pPlayer->isPvpEnnemy(civToDisplay))
{
if (pPlayer->isPvpMarauder())
pvpCivLogoBmp->setTexture("pvp_enemy_marauder.tga");
else
pvpCivLogoBmp->setTexture("pvp_enemy_"+toString(civToDisplay)+".tga");
}
else
{
needCivPvpLogo = false;
}
}
CViewBitmap * pvpCultLogoBmp = dynamic_cast<CViewBitmap *>(pvpCultLogo);
if( pvpCultLogoBmp )
{
if (pPlayer->isPvpAlly(cultToDisplay))
{
if (pPlayer->isPvpPrimas())
pvpCultLogoBmp->setTexture("pvp_ally_primas.tga");
else else
pvpCultLogoBmp->setTexture("pvp_ally_"+toString(cultToDisplay)+".tga");
}
else if (pPlayer->isPvpEnnemy(cultToDisplay))
{ {
if (pPlayer->isPvpTrytonist()) if (pPlayer->getPvpMode() & PVP_MODE::PvpChallenge)
pvpCultLogoBmp->setTexture("pvp_enemy_trytonist.tga"); pvpFactionBitmap->setTexture("ico_curse.tga");
else else if (pPlayer->isNeutralPVP())
pvpCultLogoBmp->setTexture("pvp_enemy_"+toString(cultToDisplay)+".tga"); pvpFactionBitmap->setTexture("pvp_neutral.tga");
} else if (pPlayer->isAlly() && (pPlayer->getPvpMode() & PVP_MODE::PvpFactionFlagged))
pvpFactionBitmap->setTexture("pvp_ally_flag.tga");
else if (pPlayer->isAlly() && (pPlayer->getPvpMode() & PVP_MODE::PvpFaction))
pvpFactionBitmap->setTexture("pvp_ally_tag.tga");
else if (pPlayer->isEnemy() && (pPlayer->getPvpMode() & PVP_MODE::PvpFactionFlagged))
pvpFactionBitmap->setTexture("pvp_enemy_flag.tga");
else if (pPlayer->isEnemy() && (pPlayer->getPvpMode() & PVP_MODE::PvpFaction))
pvpFactionBitmap->setTexture("pvp_enemy_tag.tga");
else if (pPlayer->getPvpMode() & PVP_MODE::PvpFactionFlagged)
pvpFactionBitmap->setTexture("pvp_enemy_flag.tga");
else if (pPlayer->getPvpMode() & PVP_MODE::PvpFaction)
pvpFactionBitmap->setTexture("pvp_enemy_tag.tga");
else else
{ pvpFactionLogo->setActive(false);
needCultPvpLogo = false;
} }
} }
} }
else
{
needCivPvpLogo = false;
needCultPvpLogo = false;
}
CViewBase * pvpOutpostLogo = info->getView ("pvp_outpost_logo");
if (pvpOutpostLogo) if (pvpOutpostLogo)
{ {
if( pPlayer->getOutpostId() == 0 ) if( pPlayer->getOutpostId() != 0 )
{ pvpOutpostLogo->setActive(true);
else
pvpOutpostLogo->setActive(false); pvpOutpostLogo->setActive(false);
} }
}
CViewBase * pvpDuelLogo = info->getView ("pvp_duel_logo");
if (pvpDuelLogo) if (pvpDuelLogo)
{ {
if( !(pPlayer->getPvpMode()&PVP_MODE::PvpDuel || pPlayer->getPvpMode()&PVP_MODE::PvpChallenge) ) if( pPlayer->getPvpMode()&PVP_MODE::PvpDuel )
{ pvpDuelLogo->setActive(true);
else
pvpDuelLogo->setActive(false); pvpDuelLogo->setActive(false);
} }
}
} }
else else
{ {
CViewBase * pvpOutpostLogo = info->getView ("pvp_outpost_logo"); if (pvpFactionLogo)
pvpFactionLogo->setActive(false);
if (pvpOutpostLogo) if (pvpOutpostLogo)
pvpOutpostLogo->setActive(false); pvpOutpostLogo->setActive(false);
CViewBase * pvpDuelLogo = info->getView ("pvp_duel_logo");
if (pvpDuelLogo) if (pvpDuelLogo)
pvpDuelLogo->setActive(false); pvpDuelLogo->setActive(false);
} }
if (pvpCivLogo)
pvpCivLogo->setActive(needCivPvpLogo);
if (pvpCultLogo)
pvpCultLogo->setActive(needCultPvpLogo);
} }
// No bar and no string ? // No bar and no string ?

@ -55,6 +55,9 @@ CGroupCell::CGroupCell(const TCtorParam &param)
IgnoreMaxWidth = false; IgnoreMaxWidth = false;
IgnoreMinWidth = false; IgnoreMinWidth = false;
AddChildW = false; AddChildW = false;
_UserTexture = false;
_TextureTiled = false;
_TextureScaled = false;
setEnclosedGroupDefaultParams(); setEnclosedGroupDefaultParams();
addGroup (Group); addGroup (Group);
} }
@ -200,9 +203,49 @@ void CGroupCell::draw ()
} }
// Draw the background // Draw the background
if (BgColor.A != 0) if (_UserTexture || BgColor.A != 0)
{ {
CViewRenderer &rVR = pIM->getViewRenderer(); CViewRenderer &rVR = pIM->getViewRenderer();
if (_UserTexture)
{
CRGBA col;
if (BgColor.A == 0 )
col = CRGBA(255,255,255,255);
else
col = BgColor;
if (_TextureScaled && !_TextureTiled)
{
rVR.drawRotFlipBitmap (_RenderLayer, _XReal, _YReal,
_WReal, _HReal,
0, false,
_TextureId,
col );
}
else
{
if (!_TextureTiled)
{
rVR.draw11RotFlipBitmap (_RenderLayer, _XReal, _YReal,
0, false,
_TextureId,
col);
}
else
{
rVR.drawRotFlipBitmapTiled(_RenderLayer, _XReal, _YReal,
_WReal, _HReal,
0, false,
_TextureId,
0,
col);
}
}
}
else
{
CRGBA finalColor; CRGBA finalColor;
finalColor.modulateFromColor (BgColor, pIM->getGlobalColor()); finalColor.modulateFromColor (BgColor, pIM->getGlobalColor());
@ -213,8 +256,10 @@ void CGroupCell::draw ()
finalColor.A = (uint8) (((uint16) table->CurrentAlpha * (uint16) finalColor.A) >> 8); finalColor.A = (uint8) (((uint16) table->CurrentAlpha * (uint16) finalColor.A) >> 8);
} }
//nlinfo("Blank Texture");
rVR.drawRotFlipBitmap (_RenderLayer, _XReal, _YReal, _WReal, _HReal, 0, false, rVR.getBlankTextureId(), finalColor); rVR.drawRotFlipBitmap (_RenderLayer, _XReal, _YReal, _WReal, _HReal, 0, false, rVR.getBlankTextureId(), finalColor);
} }
}
CInterfaceGroup::draw (); CInterfaceGroup::draw ();
} }
@ -231,6 +276,40 @@ sint32 CGroupCell::getMinUsedW() const
return Group->getMinUsedW(); return Group->getMinUsedW();
} }
// ----------------------------------------------------------------------------
void CGroupCell::setTexture(const std::string & TxName)
{
if (TxName.empty() || TxName == "none")
{
_UserTexture = false;
nlinfo("Set no texture");
}
else
{
nlinfo("Set texture to cell : %s", TxName.c_str());
_UserTexture = true;
_TextureId.setTexture (TxName.c_str (), 0, 0, -1, -1, false);
}
}
// ----------------------------------------------------------------------------
void CGroupCell::setTextureTile(bool tiled)
{
if (tiled)
nlinfo("Set texture is Tiled");
_TextureTiled = tiled;
}
// ----------------------------------------------------------------------------
void CGroupCell::setTextureScale(bool scaled)
{
if (scaled)
nlinfo("Set texture is Scaled : %s");
_TextureScaled = scaled;
}
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
NLMISC_REGISTER_OBJECT(CViewBase, CGroupTable, std::string, "table"); NLMISC_REGISTER_OBJECT(CViewBase, CGroupTable, std::string, "table");

@ -80,6 +80,12 @@ public:
// The cell color // The cell color
NLMISC::CRGBA BgColor; NLMISC::CRGBA BgColor;
// Texture
CViewRenderer::CTextureId _TextureId; /// Accelerator
bool _UserTexture;
bool _TextureTiled;
bool _TextureScaled;
// Alignment // Alignment
TAlign Align; TAlign Align;
TVAlign VAlign; TVAlign VAlign;
@ -90,6 +96,11 @@ public:
// The cell is nowrap // The cell is nowrap
bool NoWrap; bool NoWrap;
void setTexture(const std::string & TxName);
void setTextureTile(bool tiled);
void setTextureScale(bool scaled);
private: private:
void setEnclosedGroupDefaultParams(); void setEnclosedGroupDefaultParams();
}; };

@ -358,15 +358,54 @@ void CGuildManager::update()
// If all is valid no more need update and if guild is opened update the interface // If all is valid no more need update and if guild is opened update the interface
if (bAllValid) if (bAllValid)
{ {
CCDBNodeLeaf* node = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_ONLINE_OFFLINE_NOTIFICATIONS_CB", false);
if (node && node->getValueBool())
{
// See if we need to show any online/offline messages
static vector<SGuildMember> CachedGuildMembers;
ucstring onlineMessage = CI18N::get("uiPlayerOnline");
ucstring offlineMessage = CI18N::get("uiPlayerOffline");
for (uint i = 0; i < _GuildMembers.size(); ++i)
{
for (uint j = 0; j < CachedGuildMembers.size(); ++j)
{
if ((CachedGuildMembers[j].Name == _GuildMembers[i].Name) &&
(CachedGuildMembers[j].Online != _GuildMembers[i].Online))
{
ucstring msg = (_GuildMembers[i].Online != ccs_offline) ? onlineMessage : offlineMessage;
strFindReplace(msg, "%s", _GuildMembers[i].Name);
string cat = getStringCategory(msg, msg);
map<string, CClientConfig::SSysInfoParam>::const_iterator it;
NLMISC::CRGBA col = CRGBA::Yellow;
it = ClientCfg.SystemInfoParams.find(toLower(cat));
if (it != ClientCfg.SystemInfoParams.end())
{
col = it->second.Color;
}
bool dummy;
PeopleInterraction.ChatInput.Guild.displayMessage(msg, col, 2, &dummy);
break;
}
}
}
CachedGuildMembers.clear();
for (uint i = 0; i < _GuildMembers.size(); ++i)
{
CachedGuildMembers.push_back(_GuildMembers[i]);
}
}
// Search for UserEntity to find our own grade // Search for UserEntity to find our own grade
if ((UserEntity != NULL) && (_GuildMembers.size() > 0)) if ((UserEntity != NULL) && (_GuildMembers.size() > 0))
{ {
uint i; uint i;
_Grade = EGSPD::CGuildGrade::Member; _Grade = EGSPD::CGuildGrade::Member;
string sUserName = strlwr(UserEntity->getEntityName().toString()); ucstring sUserName = toLower(UserEntity->getEntityName());
for (i = 0; i < _GuildMembers.size(); ++i) for (i = 0; i < _GuildMembers.size(); ++i)
{ {
if (strlwr(_GuildMembers[i].Name.toString()) == sUserName) if (toLower(_GuildMembers[i].Name) == sUserName)
{ {
_Grade = _GuildMembers[i].Grade; _Grade = _GuildMembers[i].Grade;
break; break;
@ -1048,11 +1087,27 @@ class CAHGuildSheetSetLeader : public IActionHandler
{ {
virtual void execute (CCtrlBase * /* pCaller */, const string &/* Params */) virtual void execute (CCtrlBase * /* pCaller */, const string &/* Params */)
{ {
sendMsgSetGrade(EGSPD::CGuildGrade::Leader); CInterfaceManager *pIM = CInterfaceManager::getInstance();
// Ask if they are sure
pIM->validMessageBox(CInterfaceManager::QuestionIconMsg, CI18N::get("uiQSetLeader"), "guild_member_do_change_leader");
} }
}; };
REGISTER_ACTION_HANDLER (CAHGuildSheetSetLeader, "guild_member_chg_to_leader"); REGISTER_ACTION_HANDLER (CAHGuildSheetSetLeader, "guild_member_chg_to_leader");
// ***************************************************************************
class CAHGuildSheetSetLeaderConfirm : public IActionHandler
{
virtual void execute (CCtrlBase * /* pCaller */, const string &/* Params */)
{
// Leadership change confirmed
sendMsgSetGrade(EGSPD::CGuildGrade::Leader);
}
};
REGISTER_ACTION_HANDLER (CAHGuildSheetSetLeaderConfirm, "guild_member_do_change_leader");
// *************************************************************************** // ***************************************************************************
class CAHGuildSheetSetHighOfficer : public IActionHandler class CAHGuildSheetSetHighOfficer : public IActionHandler
{ {

@ -176,13 +176,17 @@ public:
void setRightClickHandlerParams(const std::string &params) { _AHOnRightClickParams = params; } void setRightClickHandlerParams(const std::string &params) { _AHOnRightClickParams = params; }
void setOnActiveHandler(const std::string &h) { _AHOnActive = getAH(h,_AHOnActiveParams); } void setOnActiveHandler(const std::string &h) { _AHOnActive = getAH(h,_AHOnActiveParams); }
void setOnActiveParams(const std::string &p) { _AHOnActiveParams = p; } void setOnActiveParams(const std::string &p) { _AHOnActiveParams = p; }
std::string getOnActiveParams() const { return _AHOnActiveParams; }
void setOnDeactiveHandler(const std::string &h) { _AHOnDeactive = getAH(h,_AHOnDeactiveParams); } void setOnDeactiveHandler(const std::string &h) { _AHOnDeactive = getAH(h,_AHOnDeactiveParams); }
void setOnDeactiveParams(const std::string &p) { _AHOnDeactiveParams = p; } void setOnDeactiveParams(const std::string &p) { _AHOnDeactiveParams = p; }
std::string getOnDeactiveParams() const { return _AHOnDeactiveParams; }
const std::string &getLeftClickHandler() const { return getAHName(_AHOnLeftClick); } const std::string &getLeftClickHandler() const { return getAHName(_AHOnLeftClick); }
const std::string &getLeftClickHandlerParams() const { return _AHOnLeftClickParams; } const std::string &getLeftClickHandlerParams() const { return _AHOnLeftClickParams; }
const std::string &getRightClickHandler() const { return getAHName(_AHOnRightClick); }
const std::string &getRightClickHandlerParams() const { return _AHOnRightClickParams; }
const std::string &getOnActiveHandler() const { return getAHName(_AHOnActive); }
const std::string &getOnActiveParams() const { return _AHOnActiveParams; }
const std::string &getOnDeactiveHandler() const { return getAHName(_AHOnDeactive); }
const std::string &getOnDeactiveParams() const { return _AHOnDeactiveParams; }
// find a sub view/ctrl/group in this group from its id // find a sub view/ctrl/group in this group from its id
int luaFind(CLuaState &ls); int luaFind(CLuaState &ls);
@ -205,8 +209,18 @@ public:
REFLECT_LUA_METHOD("delGroup", luaDelGroup); REFLECT_LUA_METHOD("delGroup", luaDelGroup);
REFLECT_LUA_METHOD("getNumGroups", luaGetNumGroups); REFLECT_LUA_METHOD("getNumGroups", luaGetNumGroups);
REFLECT_LUA_METHOD("getGroup", luaGetGroup); REFLECT_LUA_METHOD("getGroup", luaGetGroup);
REFLECT_STRING ("left_click", getLeftClickHandler, setLeftClickHandler);
REFLECT_STRING ("right_click", getRightClickHandler, setRightClickHandler);
REFLECT_STRING ("left_click_params", getLeftClickHandlerParams, setLeftClickHandlerParams);
REFLECT_STRING ("right_click_params", getRightClickHandlerParams, setRightClickHandlerParams);
REFLECT_STRING ("on_active", getOnActiveHandler, setOnActiveHandler);
REFLECT_STRING ("on_active_params", getOnActiveParams, setOnActiveParams); REFLECT_STRING ("on_active_params", getOnActiveParams, setOnActiveParams);
REFLECT_STRING ("on_deactive", getOnDeactiveHandler, setOnDeactiveHandler);
REFLECT_STRING ("on_deactive_params", getOnDeactiveParams, setOnDeactiveParams); REFLECT_STRING ("on_deactive_params", getOnDeactiveParams, setOnDeactiveParams);
REFLECT_STRING ("on_enter", getAHOnEnter, setAHOnEnter);
REFLECT_STRING ("on_enter_params", getAHOnEnterParams, setAHOnEnterParams);
REFLECT_STRING ("on_escape", getAHOnEscape, setAHOnEscape);
REFLECT_STRING ("on_escape_params", getAHOnEscapeParams, setAHOnEscapeParams);
REFLECT_SINT32 ("ofsx", getOfsX, setOfsX); REFLECT_SINT32 ("ofsx", getOfsX, setOfsX);
REFLECT_SINT32 ("ofsy", getOfsY, setOfsY); REFLECT_SINT32 ("ofsy", getOfsY, setOfsY);
REFLECT_BOOL("child_resize_w", getResizeFromChildW, setResizeFromChildW); REFLECT_BOOL("child_resize_w", getResizeFromChildW, setResizeFromChildW);

@ -824,6 +824,21 @@ void CInterfaceManager::initInGame()
{ {
gc->setTarget(gc->getSavedTarget()); gc->setTarget(gc->getSavedTarget());
} }
CCDBNodeLeaf *node = getDbProp("UI:SAVE:CHATLOG_STATE", false);
if (node)
{
_LogState = (node->getValue32() != 0);
}
if (_LogState)
{
displaySystemInfo(CI18N::get("uiLogTurnedOn"));
}
else
{
displaySystemInfo(CI18N::get("uiLogTurnedOff"));
}
} }
// ------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------
@ -2372,7 +2387,8 @@ void CInterfaceManager::drawContextHelp ()
if(newCtrl) if(newCtrl)
{ {
// get the text // get the text
newCtrl->getContextHelpToolTip(_ContextHelpText); //newCtrl->getContextHelpToolTip(_ContextHelpText);
newCtrl->getContextHelp(_ContextHelpText);
// UserDefined context help // UserDefined context help
if( !newCtrl->getContextHelpActionHandler().empty() ) if( !newCtrl->getContextHelpActionHandler().empty() )
{ {
@ -3408,6 +3424,13 @@ CCDBNodeLeaf* CInterfaceManager::getDbProp(const std::string & name, bool bCreat
return pDBNL; return pDBNL;
} }
// ------------------------------------------------------------------------------------------------
void CInterfaceManager::delDbProp(const std::string & name)
{
if (name.empty()) return;
_DbRootNode->removeNode( ICDBNode::CTextId(name) );
}
// ------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------
CCDBNodeBranch *CInterfaceManager::getDbBranch(const std::string &name) CCDBNodeBranch *CInterfaceManager::getDbBranch(const std::string &name)
{ {
@ -5759,7 +5782,7 @@ bool CInterfaceManager::executeLuaScript(const std::string &luaScript, bool smal
std::string msg = e.luaWhat(); std::string msg = e.luaWhat();
char filename[MAX_PATH]; char filename[MAX_PATH];
char exceptionName[MAX_PATH]; char exceptionName[MAX_PATH];
int line; uint32 line;
// Hamster: quick fix on AJM code but sscanf is still awfull // Hamster: quick fix on AJM code but sscanf is still awfull
if (sscanf(msg.c_str(), "%s: %s.lua:%d:",exceptionName, filename, &line) == 3) // NB: test not exact here, but should work in 99,9 % of cases if (sscanf(msg.c_str(), "%s: %s.lua:%d:",exceptionName, filename, &line) == 3) // NB: test not exact here, but should work in 99,9 % of cases
{ {
@ -5770,6 +5793,20 @@ bool CInterfaceManager::executeLuaScript(const std::string &luaScript, bool smal
else // AJM: handle the other 0.1% of cases else // AJM: handle the other 0.1% of cases
{ {
// Yoyo: seems that previous test doesn't work.... btw, must still print the message please... // Yoyo: seems that previous test doesn't work.... btw, must still print the message please...
std::vector<string> error;
splitString(msg.c_str(), ":", error);
if (error.size() > 3)
{
std::vector<string> contextList;
explode(luaScript, string("\n"), contextList);
fromString(error[2], line);
if (line >= 3 && contextList.size() >= line)
msg = error[0]+": \n>>> "+contextList[line-3]+"\n>>> "+contextList[line-2]+"\n>>> "+contextList[line-1]+"\nError:"+error[2]+": "+error[3];
else if (line >= 2 && contextList.size() >= line)
msg = error[0]+": \n>>>"+contextList[line-2]+"\n>>>"+contextList[line-1]+"\nError:"+error[2]+": "+error[3];
else if (line >= 1 && contextList.size() >= line)
msg = error[0]+": \n>>>"+contextList[line-1]+"\nError:"+error[2]+": "+error[3];
}
nlwarning(formatLuaErrorNlWarn(msg).c_str()); nlwarning(formatLuaErrorNlWarn(msg).c_str());
displaySystemInfo(formatLuaErrorSysInfo(msg)); displaySystemInfo(formatLuaErrorSysInfo(msg));
} }

@ -232,6 +232,7 @@ public:
CCDBNodeBranch *getDB() const { return _DbRootNode; } CCDBNodeBranch *getDB() const { return _DbRootNode; }
// yoyo: should avoid to try creating DbPropr with this system... very dangerous // yoyo: should avoid to try creating DbPropr with this system... very dangerous
CCDBNodeLeaf* getDbProp (const std::string & name, bool bCreate=true); CCDBNodeLeaf* getDbProp (const std::string & name, bool bCreate=true);
void delDbProp(const std::string & name);
// get a Db Branch by its name. NULL if don't exist or not a branch (never try to create it) // get a Db Branch by its name. NULL if don't exist or not a branch (never try to create it)
CCDBNodeBranch *getDbBranch(const std::string &name); CCDBNodeBranch *getDbBranch(const std::string &name);
// return the DB as an int32. return 0 if the DB does not exist (never create) // return the DB as an int32. return 0 if the DB does not exist (never create)

@ -517,7 +517,7 @@ bool CInterfaceParser::parseInterface (const std::vector<std::string> & strings,
{ {
bool ok; bool ok;
bool needCheck = checkInData; bool needCheck = false;
#if !FINAL_VERSION #if !FINAL_VERSION
needCheck = false; needCheck = false;
@ -554,10 +554,12 @@ bool CInterfaceParser::parseInterface (const std::vector<std::string> & strings,
string::size_type pos = filename.find ("@"); string::size_type pos = filename.find ("@");
if (pos != string::npos) if (pos != string::npos)
{ {
std::string bigFilename = CBigFile::getInstance().getBigFileName(filename.substr(0, pos)); vector<string> bigFilePaths;
std::string path = "data/"+filename.substr(0, pos); CBigFile::getInstance().getBigFilePaths(bigFilePaths);
if (CBigFile::getInstance().getBigFileName(filename.substr(0, pos)) != "data/"+filename.substr(0, pos))
isInData = bigFilename.find(path) != std::string::npos; isInData = false;
else
isInData = true;
} }
if ((needCheck && !isInData) || !file.open (CPath::lookup(firstFileName))) if ((needCheck && !isInData) || !file.open (CPath::lookup(firstFileName)))
@ -4685,7 +4687,7 @@ bool CInterfaceParser::loadLUA(const std::string &fileName, std::string &error)
{ {
// get file // get file
bool needCheck = true; bool needCheck = false;
#if !FINAL_VERSION #if !FINAL_VERSION
needCheck = false; needCheck = false;
@ -4702,10 +4704,10 @@ bool CInterfaceParser::loadLUA(const std::string &fileName, std::string &error)
std::string::size_type pos = pathName.find("@"); std::string::size_type pos = pathName.find("@");
if (pos != string::npos) if (pos != string::npos)
{ {
std::string bigFilename = CBigFile::getInstance().getBigFileName(pathName.substr(0, pos)); if (CBigFile::getInstance().getBigFileName(pathName.substr(0, pos)) != "data/"+pathName.substr(0, pos))
std::string path = "data/"+pathName.substr(0, pos); isInData = false;
else
isInData = bigFilename.find(path) != std::string::npos; isInData = true;
} }
if (needCheck && !isInData) if (needCheck && !isInData)

@ -44,12 +44,14 @@
#include "../sheet_manager.h" #include "../sheet_manager.h"
#include "game_share/slot_equipment.h" #include "game_share/slot_equipment.h"
#include "game_share/animal_status.h" #include "game_share/animal_status.h"
#include "game_share/bot_chat_types.h"
#include "../client_cfg.h" #include "../client_cfg.h"
using namespace std; using namespace std;
using namespace NLMISC; using namespace NLMISC;
extern NLMISC::CLog g_log;
// Context help // Context help
extern void contextHelp (const std::string &help); extern void contextHelp (const std::string &help);
@ -131,6 +133,7 @@ void CItemImage::build(CCDBNodeBranch *branch)
Weight = dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("WEIGHT"), false)); Weight = dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("WEIGHT"), false));
NameId = dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("NAMEID"), false)); NameId = dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("NAMEID"), false));
InfoVersion= dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("INFO_VERSION"), false)); InfoVersion= dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("INFO_VERSION"), false));
ResaleFlag = dynamic_cast<CCDBNodeLeaf *>(branch->getNode(ICDBNode::CTextId("RESALE_FLAG"), false));
// Should always have at least those one:(ie all but Price) // Should always have at least those one:(ie all but Price)
nlassert(Sheet && Quality && Quantity && UserColor && Weight && NameId && InfoVersion); nlassert(Sheet && Quality && Quantity && UserColor && Weight && NameId && InfoVersion);
@ -1998,6 +2001,9 @@ bool SBagOptions::parse(xmlNodePtr cur, CInterfaceGroup * /* parentGroup */)
prop = xmlGetProp (cur, (xmlChar*)"filter_missmp"); prop = xmlGetProp (cur, (xmlChar*)"filter_missmp");
if (prop) DbFilterMissMP = pIM->getDbProp(prop); if (prop) DbFilterMissMP = pIM->getDbProp(prop);
prop = xmlGetProp (cur, (xmlChar*)"filter_tp");
if (prop) DbFilterTP = pIM->getDbProp(prop);
return true; return true;
} }
@ -2041,6 +2047,13 @@ bool SBagOptions::isSomethingChanged()
LastDbFilterMissMP = (DbFilterMissMP->getValue8() != 0); LastDbFilterMissMP = (DbFilterMissMP->getValue8() != 0);
} }
if (DbFilterTP != NULL)
if ((DbFilterTP->getValue8() != 0) != LastDbFilterTP)
{
bRet = true;
LastDbFilterTP = (DbFilterTP->getValue8() != 0);
}
return bRet; return bRet;
} }
@ -2054,25 +2067,33 @@ bool SBagOptions::canDisplay(CDBCtrlSheet *pCS) const
bool bFilterTool = getFilterTool(); bool bFilterTool = getFilterTool();
bool bFilterMP = getFilterMP(); bool bFilterMP = getFilterMP();
bool bFilterMissMP = getFilterMissMP(); bool bFilterMissMP = getFilterMissMP();
bool bFilterTP = getFilterTP();
const CItemSheet *pIS = pCS->asItemSheet(); const CItemSheet *pIS = pCS->asItemSheet();
if (pIS != NULL) if (pIS != NULL)
{ {
// Armor // Armor
if ((pIS->Family == ITEMFAMILY::ARMOR) || (pIS->Family == ITEMFAMILY::JEWELRY)) if ((pIS->Family == ITEMFAMILY::ARMOR) ||
(pIS->Family == ITEMFAMILY::JEWELRY))
if (!bFilterArmor) bDisplay = false; if (!bFilterArmor) bDisplay = false;
// Weapon // Weapon
if ((pIS->Family == ITEMFAMILY::SHIELD) || (pIS->Family == ITEMFAMILY::MELEE_WEAPON) || if ((pIS->Family == ITEMFAMILY::SHIELD) ||
(pIS->Family == ITEMFAMILY::RANGE_WEAPON) || (pIS->Family == ITEMFAMILY::AMMO) || (pIS->Family == ITEMFAMILY::MELEE_WEAPON) ||
(pIS->Family == ITEMFAMILY::CRYSTALLIZED_SPELL) || (pIS->Family == ITEMFAMILY::ITEM_SAP_RECHARGE) || (pIS->Family == ITEMFAMILY::RANGE_WEAPON) ||
(pIS->Family == ITEMFAMILY::AMMO) ||
(pIS->Family == ITEMFAMILY::CRYSTALLIZED_SPELL) ||
(pIS->Family == ITEMFAMILY::ITEM_SAP_RECHARGE) ||
(pIS->Family == ITEMFAMILY::BRICK) ) (pIS->Family == ITEMFAMILY::BRICK) )
if (!bFilterWeapon) bDisplay = false; if (!bFilterWeapon) bDisplay = false;
// Tool // Tool
if ((pIS->Family == ITEMFAMILY::CRAFTING_TOOL) || (pIS->Family == ITEMFAMILY::HARVEST_TOOL) || if ((pIS->Family == ITEMFAMILY::CRAFTING_TOOL) ||
(pIS->Family == ITEMFAMILY::TAMING_TOOL) || (pIS->Family == ITEMFAMILY::TRAINING_TOOL) || (pIS->Family == ITEMFAMILY::HARVEST_TOOL) ||
(pIS->Family == ITEMFAMILY::BAG) || (pIS->Family == ITEMFAMILY::PET_ANIMAL_TICKET) ) (pIS->Family == ITEMFAMILY::TAMING_TOOL) ||
(pIS->Family == ITEMFAMILY::TRAINING_TOOL) ||
(pIS->Family == ITEMFAMILY::BAG) ||
(pIS->Family == ITEMFAMILY::PET_ANIMAL_TICKET) )
if (!bFilterTool) bDisplay = false; if (!bFilterTool) bDisplay = false;
// MP // MP
@ -2081,9 +2102,15 @@ bool SBagOptions::canDisplay(CDBCtrlSheet *pCS) const
// Mission MP // Mission MP
if ((pIS->Family == ITEMFAMILY::MISSION_ITEM) || if ((pIS->Family == ITEMFAMILY::MISSION_ITEM) ||
(pIS->Family == ITEMFAMILY::XP_CATALYSER) ||
(pIS->Family == ITEMFAMILY::CONSUMABLE) ||
((pIS->Family == ITEMFAMILY::RAW_MATERIAL) && !pIS->canBuildSomeItemPart())) ((pIS->Family == ITEMFAMILY::RAW_MATERIAL) && !pIS->canBuildSomeItemPart()))
if (!bFilterMissMP) bDisplay = false; if (!bFilterMissMP) bDisplay = false;
// Teleporter Pacts
if ((pIS->Family == ITEMFAMILY::TELEPORT))
if (!bFilterTP) bDisplay = false;
// Jobs Items // Jobs Items
if (pIS->Id.toString().substr(0, 6) == "rpjob_") if (pIS->Id.toString().substr(0, 6) == "rpjob_")
bDisplay = false; bDisplay = false;
@ -2776,6 +2803,37 @@ public:
REGISTER_ACTION_HANDLER( CHandlerInvAutoEquip, "inv_auto_equip" ); REGISTER_ACTION_HANDLER( CHandlerInvAutoEquip, "inv_auto_equip" );
// **********************************************************************************************************
class CHandlerLockInvItem : public IActionHandler
{
void execute (CCtrlBase *pCaller, const std::string &sParams)
{
// get the calling item
CDBCtrlSheet *item = CDBCtrlSheet::getCurrSelSheet();
if ( ! item)
{
nlwarning("<CHandlerDestroyItem::execute> no caller sheet found");
return;
}
string lock = "1";
if (item->getLockedByOwner())
{
lock = "0";
}
uint32 slot = item->getIndexInDB();
uint32 inv = item->getInventoryIndex();
INVENTORIES::TInventory inventory = INVENTORIES::UNDEFINED;
inventory = (INVENTORIES::TInventory)(inv);
if (inventory == INVENTORIES::UNDEFINED)
{
return;
}
NLMISC::ICommand::execute("a lockItem " + INVENTORIES::toString(inventory) + " " + toString(slot) + " " + lock, g_log);
}
};
REGISTER_ACTION_HANDLER( CHandlerLockInvItem, "lock_inv_item" );
// *************************************************************************** // ***************************************************************************
// Inventory Temporary // Inventory Temporary
@ -2844,11 +2902,11 @@ class CHandlerInvTempAll : public IActionHandler
nlctassert(MAX_INVENTORY_ANIMAL==4); nlctassert(MAX_INVENTORY_ANIMAL==4);
if (pInv->isInventoryAvailable(INVENTORIES::pet_animal1)) if (pInv->isInventoryAvailable(INVENTORIES::pet_animal1))
BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(2), pInv->getMaxBagBulk(2))); BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(1), pInv->getMaxBagBulk(1)));
if (pInv->isInventoryAvailable(INVENTORIES::pet_animal2)) if (pInv->isInventoryAvailable(INVENTORIES::pet_animal2))
BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(3), pInv->getMaxBagBulk(3))); BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(2), pInv->getMaxBagBulk(2)));
if (pInv->isInventoryAvailable(INVENTORIES::pet_animal3)) if (pInv->isInventoryAvailable(INVENTORIES::pet_animal3))
BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(4), pInv->getMaxBagBulk(4))); BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(3), pInv->getMaxBagBulk(3)));
if (pInv->isInventoryAvailable(INVENTORIES::pet_animal4)) if (pInv->isInventoryAvailable(INVENTORIES::pet_animal4))
BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(4), pInv->getMaxBagBulk(4))); BagsBulk.push_back(pair <double, double>(pInv->getBagBulk(4), pInv->getMaxBagBulk(4)));

@ -25,6 +25,7 @@
#include "game_share/item_infos.h" #include "game_share/item_infos.h"
#include "game_share/temp_inventory_mode.h" #include "game_share/temp_inventory_mode.h"
#include "game_share/inventories.h" #include "game_share/inventories.h"
#include "game_share/bot_chat_types.h"
class CCDBNodeBranch; class CCDBNodeBranch;
class CDBCtrlSheet; class CDBCtrlSheet;
@ -62,6 +63,7 @@ public:
CCDBNodeLeaf *Weight; CCDBNodeLeaf *Weight;
CCDBNodeLeaf *NameId; CCDBNodeLeaf *NameId;
CCDBNodeLeaf *InfoVersion; CCDBNodeLeaf *InfoVersion;
CCDBNodeLeaf *ResaleFlag;
public: public:
// ctor // ctor
@ -77,6 +79,8 @@ public:
uint32 getWeight() const { return (uint32) (Weight ? Weight->getValue32() : 0); } uint32 getWeight() const { return (uint32) (Weight ? Weight->getValue32() : 0); }
uint32 getNameId() const { return (uint32) (NameId ? NameId->getValue32() : 0); } uint32 getNameId() const { return (uint32) (NameId ? NameId->getValue32() : 0); }
uint8 getInfoVersion() const { return (uint8) (InfoVersion ? (uint8) InfoVersion->getValue8() : 0); } uint8 getInfoVersion() const { return (uint8) (InfoVersion ? (uint8) InfoVersion->getValue8() : 0); }
uint8 getResaleFlag() const { return (uint8) (ResaleFlag ? (uint8) ResaleFlag->getValue8() : 0); }
bool getLockedByOwner() const { return (bool) (ResaleFlag ? (ResaleFlag->getValue8() == BOTCHATTYPE::ResaleKOLockedByOwner) : false); }
// //
void setSheetID(uint32 si) { if (Sheet) Sheet->setValue32((sint32) si); } void setSheetID(uint32 si) { if (Sheet) Sheet->setValue32((sint32) si); }
void setQuality(uint16 quality) { if (Quality) Quality->setValue16((sint16) quality); } void setQuality(uint16 quality) { if (Quality) Quality->setValue16((sint16) quality); }
@ -86,6 +90,7 @@ public:
void setWeight(uint32 wgt) { if (Weight) Weight->setValue32((sint32) wgt); } void setWeight(uint32 wgt) { if (Weight) Weight->setValue32((sint32) wgt); }
void setNameId(uint32 nid) { if (NameId) NameId->setValue32((sint32) nid); } void setNameId(uint32 nid) { if (NameId) NameId->setValue32((sint32) nid); }
void setInfoVersion(uint8 iv) { if (InfoVersion) InfoVersion->setValue8((sint8) iv); } void setInfoVersion(uint8 iv) { if (InfoVersion) InfoVersion->setValue8((sint8) iv); }
void setResaleFlag(uint8 resale) { if (ResaleFlag) ResaleFlag->setValue8(resale); }
}; };
@ -504,18 +509,20 @@ struct SBagOptions
CCDBNodeLeaf *DbFilterTool; CCDBNodeLeaf *DbFilterTool;
CCDBNodeLeaf *DbFilterMP; CCDBNodeLeaf *DbFilterMP;
CCDBNodeLeaf *DbFilterMissMP; CCDBNodeLeaf *DbFilterMissMP;
CCDBNodeLeaf *DbFilterTP;
bool LastDbFilterArmor; bool LastDbFilterArmor;
bool LastDbFilterWeapon; bool LastDbFilterWeapon;
bool LastDbFilterTool; bool LastDbFilterTool;
bool LastDbFilterMP; bool LastDbFilterMP;
bool LastDbFilterMissMP; bool LastDbFilterMissMP;
bool LastDbFilterTP;
// ----------------------- // -----------------------
SBagOptions() SBagOptions()
{ {
InvType = CInventoryManager::InvUnknown; InvType = CInventoryManager::InvUnknown;
DbFilterArmor = DbFilterWeapon = DbFilterTool = DbFilterMP = DbFilterMissMP = NULL; DbFilterArmor = DbFilterWeapon = DbFilterTool = DbFilterMP = DbFilterMissMP = DbFilterTP = NULL;
LastDbFilterArmor = LastDbFilterWeapon = LastDbFilterTool = LastDbFilterMP = LastDbFilterMissMP = false; LastDbFilterArmor = LastDbFilterWeapon = LastDbFilterTool = LastDbFilterMP = LastDbFilterMissMP = LastDbFilterTP = false;
} }
bool parse (xmlNodePtr cur, CInterfaceGroup *parentGroup); bool parse (xmlNodePtr cur, CInterfaceGroup *parentGroup);
@ -552,6 +559,12 @@ struct SBagOptions
return (DbFilterMissMP->getValue8()!=0); return (DbFilterMissMP->getValue8()!=0);
} }
bool getFilterTP() const
{
if (DbFilterTP == NULL) return true;
return (DbFilterTP->getValue8() != 0);
}
// Return true if the sheet can be displayed due to filters // Return true if the sheet can be displayed due to filters
bool canDisplay(CDBCtrlSheet *pCS) const; bool canDisplay(CDBCtrlSheet *pCS) const;
}; };

@ -143,7 +143,7 @@ extern NLMISC::CLog g_log;
extern CContinentManager ContinentMngr; extern CContinentManager ContinentMngr;
extern uint8 PlayerSelectedSlot; extern uint8 PlayerSelectedSlot;
extern CClientChatManager ChatMngr; extern CClientChatManager ChatMngr;
extern void addWebIGParams (string &url); extern void addWebIGParams (string &url, bool trustedDomain);
// declare ostream << operator for ucstring -> registration of ucstring iin luabind will build a 'tostring' function from it // declare ostream << operator for ucstring -> registration of ucstring iin luabind will build a 'tostring' function from it
std::ostream &operator<<(std::ostream &str, const ucstring &value) std::ostream &operator<<(std::ostream &str, const ucstring &value)
@ -1323,6 +1323,7 @@ void CLuaIHM::registerIHM(CLuaState &ls)
ls.registerFunc("getIndexInDB", getIndexInDB); ls.registerFunc("getIndexInDB", getIndexInDB);
ls.registerFunc("getUIId", getUIId); ls.registerFunc("getUIId", getUIId);
ls.registerFunc("createGroupInstance", createGroupInstance); ls.registerFunc("createGroupInstance", createGroupInstance);
ls.registerFunc("createRootGroupInstance", createRootGroupInstance);
ls.registerFunc("createUIElement", createUIElement); ls.registerFunc("createUIElement", createUIElement);
ls.registerFunc("launchContextMenuInGame", launchContextMenuInGame); ls.registerFunc("launchContextMenuInGame", launchContextMenuInGame);
ls.registerFunc("parseInterfaceFromString", parseInterfaceFromString); ls.registerFunc("parseInterfaceFromString", parseInterfaceFromString);
@ -1356,6 +1357,19 @@ void CLuaIHM::registerIHM(CLuaState &ls)
ls.registerFunc("enableModalWindow", enableModalWindow); ls.registerFunc("enableModalWindow", enableModalWindow);
ls.registerFunc("disableModalWindow", disableModalWindow); ls.registerFunc("disableModalWindow", disableModalWindow);
ls.registerFunc("getPlayerPos", getPlayerPos); ls.registerFunc("getPlayerPos", getPlayerPos);
ls.registerFunc("getPlayerFront", getPlayerFront);
ls.registerFunc("getPlayerDirection", getPlayerDirection);
ls.registerFunc("getPlayerGender", getPlayerGender);
ls.registerFunc("getPlayerName", getPlayerName);
ls.registerFunc("getPlayerTitleRaw", getPlayerTitleRaw);
ls.registerFunc("getPlayerTitle", getPlayerTitle);
ls.registerFunc("getTargetPos", getTargetPos);
ls.registerFunc("getTargetFront", getTargetFront);
ls.registerFunc("getTargetDirection", getTargetDirection);
ls.registerFunc("getTargetGender", getTargetGender);
ls.registerFunc("getTargetName", getTargetName);
ls.registerFunc("getTargetTitleRaw", getTargetTitleRaw);
ls.registerFunc("getTargetTitle", getTargetTitle);
ls.registerFunc("addSearchPathUser", addSearchPathUser); ls.registerFunc("addSearchPathUser", addSearchPathUser);
ls.registerFunc("displaySystemInfo", displaySystemInfo); ls.registerFunc("displaySystemInfo", displaySystemInfo);
ls.registerFunc("disableContextHelpForControl", disableContextHelpForControl); ls.registerFunc("disableContextHelpForControl", disableContextHelpForControl);
@ -1363,6 +1377,7 @@ void CLuaIHM::registerIHM(CLuaState &ls)
ls.registerFunc("setWeatherValue", setWeatherValue); ls.registerFunc("setWeatherValue", setWeatherValue);
ls.registerFunc("getWeatherValue", getWeatherValue); ls.registerFunc("getWeatherValue", getWeatherValue);
ls.registerFunc("getCompleteIslands", getCompleteIslands); ls.registerFunc("getCompleteIslands", getCompleteIslands);
ls.registerFunc("displayBubble", displayBubble);
ls.registerFunc("getIslandId", getIslandId); ls.registerFunc("getIslandId", getIslandId);
ls.registerFunc("getClientCfgVar", getClientCfgVar); ls.registerFunc("getClientCfgVar", getClientCfgVar);
ls.registerFunc("isPlayerFreeTrial", isPlayerFreeTrial); ls.registerFunc("isPlayerFreeTrial", isPlayerFreeTrial);
@ -1370,14 +1385,18 @@ void CLuaIHM::registerIHM(CLuaState &ls)
ls.registerFunc("isInRingMode", isInRingMode); ls.registerFunc("isInRingMode", isInRingMode);
ls.registerFunc("getUserRace", getUserRace); ls.registerFunc("getUserRace", getUserRace);
ls.registerFunc("getSheet2idx", getSheet2idx); ls.registerFunc("getSheet2idx", getSheet2idx);
ls.registerFunc("getTargetSlot", getTargetSlot);
ls.registerFunc("getSlotDataSetId", getSlotDataSetId);
// Through LUABind API // Through LUABind API
lua_State *L= ls.getStatePointer(); lua_State *L= ls.getStatePointer();
luabind::module(L) luabind::module(L)
[ [
LUABIND_FUNC(addDbProp),
LUABIND_FUNC(getDbProp), LUABIND_FUNC(getDbProp),
LUABIND_FUNC(setDbProp), LUABIND_FUNC(setDbProp),
LUABIND_FUNC(delDbProp),
LUABIND_FUNC(debugInfo), LUABIND_FUNC(debugInfo),
LUABIND_FUNC(rawDebugInfo), LUABIND_FUNC(rawDebugInfo),
LUABIND_FUNC(dumpCallStack), LUABIND_FUNC(dumpCallStack),
@ -1456,9 +1475,16 @@ void CLuaIHM::registerIHM(CLuaState &ls)
luabind::def("shellExecute", CMiscFunctions::shellExecute), luabind::def("shellExecute", CMiscFunctions::shellExecute),
LUABIND_FUNC(getPlayerLevel), LUABIND_FUNC(getPlayerLevel),
LUABIND_FUNC(getPlayerVpa),
LUABIND_FUNC(getPlayerVpb),
LUABIND_FUNC(getPlayerVpc),
LUABIND_FUNC(getTargetLevel), LUABIND_FUNC(getTargetLevel),
LUABIND_FUNC(getTargetForceRegion), LUABIND_FUNC(getTargetForceRegion),
LUABIND_FUNC(getTargetLevelForce), LUABIND_FUNC(getTargetLevelForce),
LUABIND_FUNC(getTargetSheet),
LUABIND_FUNC(getTargetVpa),
LUABIND_FUNC(getTargetVpb),
LUABIND_FUNC(getTargetVpc),
LUABIND_FUNC(isTargetNPC), LUABIND_FUNC(isTargetNPC),
LUABIND_FUNC(isTargetPlayer), // return 'true' if the target is an npc LUABIND_FUNC(isTargetPlayer), // return 'true' if the target is an npc
LUABIND_FUNC(isTargetUser), LUABIND_FUNC(isTargetUser),
@ -1686,12 +1712,60 @@ void CLuaIHM::setDbProp(const std::string &dbProp, sint32 value)
// Write to the DB if found // Write to the DB if found
CInterfaceManager *pIM= CInterfaceManager::getInstance(); CInterfaceManager *pIM= CInterfaceManager::getInstance();
CCDBNodeLeaf *node= pIM->getDbProp(dbProp, false); CCDBNodeLeaf *node= pIM->getDbProp(dbProp, false);
if(node) if(node)
node->setValue32(value); node->setValue32(value);
else else
debugInfo(toString("setDbProp(): '%s' dbProp Not found", dbProp.c_str())); debugInfo(toString("setDbProp(): '%s' dbProp Not found", dbProp.c_str()));
} }
void CLuaIHM::delDbProp(const string &dbProp)
{
//H_AUTO(Lua_CLuaIHM_setDbProp)
// Do not allow Write on SERVER: or LOCAL:
static const string dbServer= "SERVER:";
static const string dbLocal= "LOCAL:";
static const string dbLocalR2= "LOCAL:R2";
if( (0==dbProp.compare(0, dbServer.size(), dbServer)) ||
(0==dbProp.compare(0, dbLocal.size(), dbLocal))
)
{
if (0!=dbProp.compare(0, dbLocalR2.size(), dbLocalR2))
{
nlstop;
throw ELuaIHMException("setDbProp(): You are not allowed to write on 'SERVER:...' or 'LOCAL:...' database");
}
}
// Write to the DB if found
CInterfaceManager *pIM= CInterfaceManager::getInstance();
pIM->delDbProp(dbProp);
}
void CLuaIHM::addDbProp(const std::string &dbProp, sint32 value)
{
//H_AUTO(Lua_CLuaIHM_setDbProp)
// Do not allow Write on SERVER: or LOCAL:
static const std::string dbServer= "SERVER:";
static const std::string dbLocal= "LOCAL:";
static const std::string dbLocalR2= "LOCAL:R2";
if( (0==dbProp.compare(0, dbServer.size(), dbServer)) ||
(0==dbProp.compare(0, dbLocal.size(), dbLocal))
)
{
if (0!=dbProp.compare(0, dbLocalR2.size(), dbLocalR2))
{
nlstop;
throw ELuaIHMException("setDbProp(): You are not allowed to write on 'SERVER:...' or 'LOCAL:...' database");
}
}
// Write to the DB if found
CInterfaceManager *pIM= CInterfaceManager::getInstance();
CCDBNodeLeaf *node= pIM->getDbProp(dbProp, true);
if(node)
node->setValue32(value);
}
// *************************************************************************** // ***************************************************************************
void CLuaIHM::debugInfo(const std::string &cstDbg) void CLuaIHM::debugInfo(const std::string &cstDbg)
@ -1865,7 +1939,21 @@ std::string CLuaIHM::getDefine(const std::string &def)
// *************************************************************************** // ***************************************************************************
static CEntityCL *getTargetSlot() static sint32 getTargetSlotNr()
{
const char *dbPath = "UI:VARIABLES:TARGET:SLOT";
CInterfaceManager *im = CInterfaceManager::getInstance();
CCDBNodeLeaf *node = im->getDbProp(dbPath, false);
if (!node) return NULL;
if ((uint8) node->getValue32() == (uint8) CLFECOMMON::INVALID_SLOT)
{
return NULL;
}
return node->getValue32();
}
// ***************************************************************************
static CEntityCL *getTargetEntity()
{ {
const char *dbPath = "UI:VARIABLES:TARGET:SLOT"; const char *dbPath = "UI:VARIABLES:TARGET:SLOT";
CInterfaceManager *im = CInterfaceManager::getInstance(); CInterfaceManager *im = CInterfaceManager::getInstance();
@ -1878,6 +1966,12 @@ static CEntityCL *getTargetSlot()
return EntitiesMngr.entity((uint) node->getValue32()); return EntitiesMngr.entity((uint) node->getValue32());
} }
// ***************************************************************************
static CEntityCL *getSlotEntity(uint slot)
{
return EntitiesMngr.entity(slot);
}
// *************************************************************************** // ***************************************************************************
sint32 CLuaIHM::getPlayerLevel() sint32 CLuaIHM::getPlayerLevel()
{ {
@ -1890,10 +1984,31 @@ sint32 CLuaIHM::getPlayerLevel()
return sint32(maxskill); return sint32(maxskill);
} }
// ***************************************************************************
sint64 CLuaIHM::getPlayerVpa()
{
sint64 prop = CInterfaceManager::getInstance()->getDbProp("SERVER:Entities:E0:P"+toString("%d", CLFECOMMON::PROPERTY_VPA))->getValue64();
return prop;
}
// ***************************************************************************
sint64 CLuaIHM::getPlayerVpb()
{
sint64 prop = CInterfaceManager::getInstance()->getDbProp("SERVER:Entities:E0:P"+toString("%d", CLFECOMMON::PROPERTY_VPB))->getValue64();
return prop;
}
// ***************************************************************************
sint64 CLuaIHM::getPlayerVpc()
{
sint64 prop = CInterfaceManager::getInstance()->getDbProp("SERVER:Entities:E0:P"+toString("%d", CLFECOMMON::PROPERTY_VPB))->getValue64();
return prop;
}
// *************************************************************************** // ***************************************************************************
sint32 CLuaIHM::getTargetLevel() sint32 CLuaIHM::getTargetLevel()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return -1; if (!target) return -1;
if ( target->isPlayer() ) if ( target->isPlayer() )
{ {
@ -1913,10 +2028,52 @@ sint32 CLuaIHM::getTargetLevel()
return -1; return -1;
} }
// ***************************************************************************
ucstring CLuaIHM::getTargetSheet()
{
CEntityCL *target = getTargetEntity();
if (!target) return "";
return target->sheetId().toString();
}
// ***************************************************************************
sint64 CLuaIHM::getTargetVpa()
{
CEntityCL *target = getTargetEntity();
if (!target) return 0;
sint64 prop = CInterfaceManager::getInstance()->getDbProp("SERVER:Entities:E"+toString("%d", getTargetSlotNr())+":P"+toString("%d", CLFECOMMON::PROPERTY_VPA))->getValue64();
return prop;
}
// ***************************************************************************
sint64 CLuaIHM::getTargetVpb()
{
CEntityCL *target = getTargetEntity();
if (!target) return 0;
sint64 prop = CInterfaceManager::getInstance()->getDbProp("SERVER:Entities:E"+toString("%d", getTargetSlotNr())+":P"+toString("%d", CLFECOMMON::PROPERTY_VPB))->getValue64();
return prop;
}
// ***************************************************************************
sint64 CLuaIHM::getTargetVpc()
{
CEntityCL *target = getTargetEntity();
if (!target) return 0;
sint64 prop = CInterfaceManager::getInstance()->getDbProp("SERVER:Entities:E"+toString("%d", getTargetSlotNr())+":P"+toString("%d", CLFECOMMON::PROPERTY_VPB))->getValue64();
return prop;
}
// *************************************************************************** // ***************************************************************************
sint32 CLuaIHM::getTargetForceRegion() sint32 CLuaIHM::getTargetForceRegion()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return -1; if (!target) return -1;
if ( target->isPlayer() ) if ( target->isPlayer() )
{ {
@ -1944,7 +2101,7 @@ sint32 CLuaIHM::getTargetForceRegion()
// *************************************************************************** // ***************************************************************************
sint32 CLuaIHM::getTargetLevelForce() sint32 CLuaIHM::getTargetLevelForce()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return -1; if (!target) return -1;
if ( target->isPlayer() ) if ( target->isPlayer() )
{ {
@ -1972,7 +2129,7 @@ sint32 CLuaIHM::getTargetLevelForce()
// *************************************************************************** // ***************************************************************************
bool CLuaIHM::isTargetNPC() bool CLuaIHM::isTargetNPC()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return false; if (!target) return false;
return target->isNPC(); return target->isNPC();
} }
@ -1980,7 +2137,7 @@ bool CLuaIHM::isTargetNPC()
// *************************************************************************** // ***************************************************************************
bool CLuaIHM::isTargetPlayer() bool CLuaIHM::isTargetPlayer()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return false; if (!target) return false;
return target->isPlayer(); return target->isPlayer();
} }
@ -1989,7 +2146,7 @@ bool CLuaIHM::isTargetPlayer()
// *************************************************************************** // ***************************************************************************
bool CLuaIHM::isTargetUser() bool CLuaIHM::isTargetUser()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return false; if (!target) return false;
return target->isUser(); return target->isUser();
} }
@ -1998,15 +2155,15 @@ bool CLuaIHM::isTargetUser()
bool CLuaIHM::isPlayerInPVPMode() bool CLuaIHM::isPlayerInPVPMode()
{ {
if (!UserEntity) return false; if (!UserEntity) return false;
return (UserEntity->getPvpMode() & PVP_MODE::PvpFaction || UserEntity->getPvpMode() & PVP_MODE::PvpFactionFlagged || UserEntity->getPvpMode() & PVP_MODE::PvpZoneFaction); return (UserEntity->getPvpMode() & PVP_MODE::PvpFaction || UserEntity->getPvpMode() & PVP_MODE::PvpFactionFlagged || UserEntity->getPvpMode() & PVP_MODE::PvpZoneFaction) != 0;
} }
// *************************************************************************** // ***************************************************************************
bool CLuaIHM::isTargetInPVPMode() bool CLuaIHM::isTargetInPVPMode()
{ {
CEntityCL *target = getTargetSlot(); CEntityCL *target = getTargetEntity();
if (!target) return false; if (!target) return false;
return (target->getPvpMode() & PVP_MODE::PvpFaction || target->getPvpMode() & PVP_MODE::PvpFactionFlagged || target->getPvpMode() & PVP_MODE::PvpZoneFaction); return (target->getPvpMode() & PVP_MODE::PvpFaction || target->getPvpMode() & PVP_MODE::PvpFactionFlagged || target->getPvpMode() & PVP_MODE::PvpZoneFaction) != 0;
} }
// *************************************************************************** // ***************************************************************************
@ -2368,6 +2525,53 @@ int CLuaIHM::createGroupInstance(CLuaState &ls)
return 1; return 1;
} }
// ***************************************************************************
int CLuaIHM::createRootGroupInstance(CLuaState &ls)
{
//H_AUTO(Lua_CLuaIHM_createGroupInstance)
const char *funcName = "createRootGroupInstance";
CLuaIHM::checkArgCount(ls, funcName, 3);
CLuaIHM::checkArgType(ls, funcName, 1, LUA_TSTRING);
CLuaIHM::checkArgType(ls, funcName, 2, LUA_TSTRING);
CLuaIHM::checkArgType(ls, funcName, 3, LUA_TTABLE);
std::vector<std::pair<std::string, std::string> > templateParams;
CLuaObject params;
params.pop(ls);
ENUM_LUA_TABLE(params, it)
{
if (!it.nextKey().isString())
{
nlwarning("%s : bad key encountered with type %s, string expected.", funcName, it.nextKey().getTypename());
continue;
}
if (!it.nextValue().isString())
{
nlwarning("%s : bad value encountered with type %s for key %s, string expected.", funcName, it.nextValue().getTypename(), it.nextKey().toString().c_str());
continue;
}
templateParams.push_back(std::pair<std::string, std::string>(it.nextKey().toString(), it.nextValue().toString())); // strange compilation bug here when I use std::make_pair ... :(
}
CInterfaceManager *im = CInterfaceManager::getInstance();
CInterfaceGroup *result = im->createGroupInstance(ls.toString(1), "ui:interface:"+string(ls.toString(2)), templateParams);
if (!result)
{
ls.pushNil();
}
else
{
result->setId("ui:interface:"+string(ls.toString(2)));
result->updateCoords();
im->addWindowToMasterGroup("ui:interface", result);
CInterfaceGroup *pRoot = dynamic_cast<CInterfaceGroup*>(im->getElementFromId("ui:interface"));
result->setParent(pRoot);
if (pRoot)
pRoot->addGroup(result);
result->setActive(true);
CLuaIHM::pushUIOnStack(ls, result);
}
return 1;
}
// *************************************************************************** // ***************************************************************************
int CLuaIHM::createUIElement(CLuaState &ls) int CLuaIHM::createUIElement(CLuaState &ls)
{ {
@ -2407,6 +2611,42 @@ int CLuaIHM::createUIElement(CLuaState &ls)
return 1; return 1;
} }
// ***************************************************************************
int CLuaIHM::displayBubble(CLuaState &ls)
{
//H_AUTO(Lua_CLuaIHM_createUIElement)
const char *funcName = "displayBubble";
CLuaIHM::checkArgCount(ls, funcName, 3);
CLuaIHM::checkArgType(ls, funcName, 1, LUA_TNUMBER);
CLuaIHM::checkArgType(ls, funcName, 2, LUA_TSTRING);
CLuaIHM::checkArgType(ls, funcName, 3, LUA_TTABLE);
std::vector<std::string> strs;
std::vector<std::string> links;
CLuaObject params;
params.pop(ls);
ENUM_LUA_TABLE(params, it)
{
if (!it.nextKey().isString())
{
nlwarning("%s : bad key encountered with type %s, string expected.", funcName, it.nextKey().getTypename());
continue;
}
if (!it.nextValue().isString())
{
nlwarning("%s : bad value encountered with type %s for key %s, string expected.", funcName, it.nextValue().getTypename(), it.nextKey().toString().c_str());
continue;
}
links.push_back(it.nextValue().toString());
strs.push_back(it.nextKey().toString());
}
InSceneBubbleManager.webIgChatOpen((uint32)ls.toNumber(1), ls.toString(2), strs, links);
return 1;
}
// *************************************************************************** // ***************************************************************************
int CLuaIHM::getCompleteIslands(CLuaState &ls) int CLuaIHM::getCompleteIslands(CLuaState &ls)
{ {
@ -3523,7 +3763,7 @@ void CLuaIHM::browseNpcWebPage(const std::string &htmlId, const std::string &url
string("&lang=") + ClientCfg.getHtmlLanguageCode() + string("&lang=") + ClientCfg.getHtmlLanguageCode() +
string("&guild_name=") + guildName; string("&guild_name=") + guildName;
} }
/* /* Already added by GroupHtml
if(webig) if(webig)
{ {
// append special webig auth params // append special webig auth params
@ -4242,6 +4482,126 @@ int CLuaIHM::getPlayerPos(CLuaState &ls)
return 3; return 3;
} }
// ***************************************************************************
int CLuaIHM::getPlayerFront(CLuaState &ls)
{
checkArgCount(ls, "getPlayerFront", 0);
ls.push(atan2(UserEntity->front().y, UserEntity->front().x));
return 1;
}
// ***************************************************************************
int CLuaIHM::getPlayerDirection(CLuaState &ls)
{
checkArgCount(ls, "getPlayerDirection", 0);
ls.push(atan2(UserEntity->dir().y, UserEntity->dir().x));
return 1;
}
// ***************************************************************************
int CLuaIHM::getPlayerGender(CLuaState &ls)
{
checkArgCount(ls, "getPlayerGender", 0);
ls.push((lua_Number)(UserEntity->getGender()));
return 1;
}
// ***************************************************************************
int CLuaIHM::getPlayerName(CLuaState &ls)
{
checkArgCount(ls, "getPlayerName", 0);
ls.push(UserEntity->getEntityName().toUtf8());
return 1;
}
// ***************************************************************************
int CLuaIHM::getPlayerTitleRaw(CLuaState &ls)
{
checkArgCount(ls, "getPlayerTitleRaw", 0);
ls.push(UserEntity->getTitleRaw().toUtf8());
return 1;
}
// ***************************************************************************
int CLuaIHM::getPlayerTitle(CLuaState &ls)
{
checkArgCount(ls, "getPlayerTitle", 0);
ls.push(UserEntity->getTitle().toUtf8());
return 1;
}
// ***************************************************************************
int CLuaIHM::getTargetPos(CLuaState &ls)
{
checkArgCount(ls, "getTargetPos", 0);
CEntityCL *target = getTargetEntity();
if (!target) return 0;
ls.push(target->pos().x);
ls.push(target->pos().y);
ls.push(target->pos().z);
return 3;
}
// ***************************************************************************
int CLuaIHM::getTargetFront(CLuaState &ls)
{
checkArgCount(ls, "getTargetFront", 0);
CEntityCL *target = getTargetEntity();
if (!target) return 0;
ls.push(atan2(target->front().y, target->front().x));
return 1;
}
// ***************************************************************************
int CLuaIHM::getTargetDirection(CLuaState &ls)
{
checkArgCount(ls, "getTargetDirection", 0);
CEntityCL *target = getTargetEntity();
if (!target) return 0;
ls.push(atan2(target->dir().y, target->dir().x));
return 1;
}
// ***************************************************************************
int CLuaIHM::getTargetGender(CLuaState &ls)
{
checkArgCount(ls, "getTargetGender", 0);
CCharacterCL* target = (CCharacterCL*)getTargetEntity();
if (!target) return (int)GSGENDER::unknown;
ls.push((lua_Number)(target->getGender()));
return 1;
}
// ***************************************************************************
int CLuaIHM::getTargetName(CLuaState &ls)
{
checkArgCount(ls, "getTargetName", 0);
CEntityCL *target = getTargetEntity();
if (!target) return 0;
ls.push(target->getEntityName().toUtf8());
return 1;
}
// ***************************************************************************
int CLuaIHM::getTargetTitleRaw(CLuaState &ls)
{
checkArgCount(ls, "getTargetTitleRaw", 0);
CEntityCL *target = getTargetEntity();
if (!target) return 0;
ls.push(target->getTitleRaw().toUtf8());
return 1;
}
// ***************************************************************************
int CLuaIHM::getTargetTitle(CLuaState &ls)
{
checkArgCount(ls, "getTargetTitle", 0);
CEntityCL *target = getTargetEntity();
if (!target) return 0;
ls.push(target->getTitle().toUtf8());
return 1;
}
// *************************************************************************** // ***************************************************************************
int CLuaIHM::addSearchPathUser(CLuaState &ls) int CLuaIHM::addSearchPathUser(CLuaState &ls)
{ {
@ -4437,3 +4797,23 @@ int CLuaIHM::getSheet2idx(CLuaState &ls)
return 1; return 1;
} }
// ***************************************************************************
int CLuaIHM::getTargetSlot(CLuaState &ls)
{
uint32 slot = (uint32)getTargetSlotNr();
ls.push((lua_Number)slot);
return 1;
}
// ***************************************************************************
int CLuaIHM::getSlotDataSetId(CLuaState &ls)
{
CLuaIHM::checkArgCount(ls, "getSlotDataSetId", 1);
CLuaIHM::checkArgType(ls, "getSlotDataSetId", 1, LUA_TNUMBER);
uint32 slot = (uint32)ls.toNumber(1);
CEntityCL *e = getSlotEntity(slot);
string id = toString(e->dataSetId());
ls.push(id);
return 1;
}

@ -185,9 +185,16 @@ private:
// LUA exported Functions with luabind // LUA exported Functions with luabind
static sint32 getPlayerLevel(); // get max level among player skills (magi, combat, crafting ,foraging) static sint32 getPlayerLevel(); // get max level among player skills (magi, combat, crafting ,foraging)
static sint64 getPlayerVpa();
static sint64 getPlayerVpb();
static sint64 getPlayerVpc();
static sint32 getTargetLevel(); // get current, precise level of the selected target, or -1 if there's no such selected target static sint32 getTargetLevel(); // get current, precise level of the selected target, or -1 if there's no such selected target
static sint32 getTargetForceRegion(); // get 'force region' for current target, or -1 if there's no selected target static sint32 getTargetForceRegion(); // get 'force region' for current target, or -1 if there's no selected target
static sint32 getTargetLevelForce(); // get 'level force' for current target, or -1 if there's no selected target static sint32 getTargetLevelForce(); // get 'level force' for current target, or -1 if there's no selected target
static ucstring getTargetSheet(); // get the name of the target sheet (like 'zoha2old.creature')
static sint64 getTargetVpa();
static sint64 getTargetVpb();
static sint64 getTargetVpc();
static bool isTargetNPC(); // return 'true' if the target is an npc static bool isTargetNPC(); // return 'true' if the target is an npc
static bool isTargetPlayer(); // return 'true' if the target is a player static bool isTargetPlayer(); // return 'true' if the target is a player
static bool isTargetUser(); // return 'true' if the target is the user static bool isTargetUser(); // return 'true' if the target is the user
@ -206,6 +213,8 @@ private:
static double getPreciseLocalTime(); static double getPreciseLocalTime();
static sint32 getDbProp(const std::string &dbProp); // return 0 if not found. static sint32 getDbProp(const std::string &dbProp); // return 0 if not found.
static void setDbProp(const std::string &dbProp, sint32 value); // Nb: the db prop is not created if not present. static void setDbProp(const std::string &dbProp, sint32 value); // Nb: the db prop is not created if not present.
static void addDbProp(const std::string &dbProp, sint32 value); // Nb: the db prop is created if not present.
static void delDbProp(const std::string &dbProp);
static std::string getDefine(const std::string &def); static std::string getDefine(const std::string &def);
static void messageBox(const ucstring &text); static void messageBox(const ucstring &text);
static void messageBox(const ucstring &text, const std::string &masterGroup); static void messageBox(const ucstring &text, const std::string &masterGroup);
@ -291,12 +300,19 @@ private:
// param 2 = id of parent where the instance will be inserted // param 2 = id of parent where the instance will be inserted
// param 3 = table with ("template_param", "template_param_value") key/value pairs // param 3 = table with ("template_param", "template_param_value") key/value pairs
// such as { id="foo", x="10" } etc. -> returns a new instance of the template, or nil on fail // such as { id="foo", x="10" } etc. -> returns a new instance of the template, or nil on fail
static int createRootGroupInstance(CLuaState &ls); // params : param 1 = template name,
// param 2 = id of parent where the instance will be inserted
// param 3 = table with ("template_param", "template_param_value") key/value pairs
// such as { id="foo", x="10" } etc. -> returns a new instance of the template, or nil on fail
static int createUIElement(CLuaState &ls); // params : param 1 = template name, static int createUIElement(CLuaState &ls); // params : param 1 = template name,
// param 2 = id of parent where the instance will be inserted // param 2 = id of parent where the instance will be inserted
// param 3 = table with ("template_param", "template_param_value") key/value pairs // param 3 = table with ("template_param", "template_param_value") key/value pairs
// such as { id="foo", x="10" } etc. -> returns a new instance of the template, or nil on fail // such as { id="foo", x="10" } etc. -> returns a new instance of the template, or nil on fail
static int displayBubble(CLuaState &ls); // params : param 1 = bot id
// param 2 = text
// param 3 = table with all strings and urls
// {"main text"="http:///", "text option 1"="http:///", "text option 2"="http:///") etc...
static int getIndexInDB(CLuaState &ls); // params: CDBCtrlSheet*.... return: index, or 0 if error static int getIndexInDB(CLuaState &ls); // params: CDBCtrlSheet*.... return: index, or 0 if error
static int getUIId(CLuaState &ls); // params: CInterfaceElement*. return: ui id (empty if error) static int getUIId(CLuaState &ls); // params: CInterfaceElement*. return: ui id (empty if error)
static int runAH(CLuaState &ls); // params: CInterfaceElement *, "ah", "params". return: none static int runAH(CLuaState &ls); // params: CInterfaceElement *, "ah", "params". return: none
@ -345,6 +361,19 @@ private:
static int enableModalWindow(CLuaState &ls); static int enableModalWindow(CLuaState &ls);
static int disableModalWindow(CLuaState &ls); static int disableModalWindow(CLuaState &ls);
static int getPlayerPos(CLuaState &ls); static int getPlayerPos(CLuaState &ls);
static int getPlayerFront(CLuaState &ls);
static int getPlayerDirection(CLuaState &ls);
static int getPlayerGender(CLuaState &ls);
static int getPlayerName(CLuaState &ls);
static int getPlayerTitleRaw(CLuaState &ls);
static int getPlayerTitle(CLuaState &ls);
static int getTargetPos(CLuaState &ls);
static int getTargetFront(CLuaState &ls);
static int getTargetDirection(CLuaState &ls);
static int getTargetGender(CLuaState &ls);
static int getTargetName(CLuaState &ls);
static int getTargetTitleRaw(CLuaState &ls);
static int getTargetTitle(CLuaState &ls);
static int addSearchPathUser(CLuaState &ls); static int addSearchPathUser(CLuaState &ls);
static int getClientCfgVar(CLuaState &ls); static int getClientCfgVar(CLuaState &ls);
static int isPlayerFreeTrial(CLuaState &ls); static int isPlayerFreeTrial(CLuaState &ls);
@ -352,6 +381,8 @@ private:
static int isInRingMode(CLuaState &ls); static int isInRingMode(CLuaState &ls);
static int getUserRace(CLuaState &ls); static int getUserRace(CLuaState &ls);
static int getSheet2idx(CLuaState &ls); static int getSheet2idx(CLuaState &ls);
static int getTargetSlot(CLuaState &ls);
static int getSlotDataSetId(CLuaState &ls);
// LUA functions exported for Dev only (debug) // LUA functions exported for Dev only (debug)

@ -40,6 +40,7 @@
#include "../net_manager.h" #include "../net_manager.h"
#include "../connection.h" #include "../connection.h"
#include "group_tab.h" #include "group_tab.h"
#include "guild_manager.h"
// Game share // Game share
#include "game_share/entity_types.h" #include "game_share/entity_types.h"
// NeL // NeL
@ -1418,7 +1419,47 @@ void CPeopleInterraction::updateContactInList(uint32 contactId, TCharConnectionS
{ {
sint index = FriendList.getIndexFromContactId(contactId); sint index = FriendList.getIndexFromContactId(contactId);
if (index != -1) if (index != -1)
{
if (FriendList.getOnline(index) != online)
{
// Only do work if online status has changed
FriendList.setOnline(index, online); FriendList.setOnline(index, online);
CCDBNodeLeaf* node = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_ONLINE_OFFLINE_NOTIFICATIONS_CB", false);
if (node && node->getValueBool())
{
// Only show the message if this player is not in my guild (because then the guild manager will show a message)
std::vector<SGuildMember> GuildMembers = CGuildManager::getInstance()->getGuildMembers();
bool bOnlyFriend = true;
ucstring name = toLower(FriendList.getName(index));
for (uint i = 0; i < GuildMembers.size(); ++i)
{
if (toLower(GuildMembers[i].Name) == name)
{
bOnlyFriend = false;
break;
}
}
// Player is not in my guild
if (bOnlyFriend)
{
ucstring msg = (online != ccs_offline) ? CI18N::get("uiPlayerOnline") : CI18N::get("uiPlayerOffline");
strFindReplace(msg, "%s", FriendList.getName(index));
string cat = getStringCategory(msg, msg);
map<string, CClientConfig::SSysInfoParam>::const_iterator it;
NLMISC::CRGBA col = CRGBA::Yellow;
it = ClientCfg.SystemInfoParams.find(toLower(cat));
if (it != ClientCfg.SystemInfoParams.end())
{
col = it->second.Color;
}
bool dummy;
PeopleInterraction.ChatInput.AroundMe.displayMessage(msg, col, 2, &dummy);
}
}
}
}
} }
else else
{ {
@ -1988,6 +2029,39 @@ public:
}; };
REGISTER_ACTION_HANDLER( CHandlerDismissMember, "dismiss_member"); REGISTER_ACTION_HANDLER( CHandlerDismissMember, "dismiss_member");
//=================================================================================================================
// Set the leader of the team
class CHandlerSetTeamLeader : public IActionHandler
{
public:
void execute (CCtrlBase * /* pCaller */, const std::string &/* sParams */)
{
// retrieve the index of the people
CPeopleList *list;
uint peopleIndex;
if (PeopleInterraction.getPeopleFromCurrentMenu(list, peopleIndex))
{
if (list == &PeopleInterraction.TeamList) // check for good list
{
/*
const string msgName = "TEAM:SET_LEADER";
CBitMemStream out;
if(GenericMsgHeaderMngr.pushNameToStream(msgName, out))
{
uint8 teamMember = (uint8)(peopleIndex);
out.serial(teamMember);
NetMngr.push(out);
//nlinfo("impulseCallBack : %s %d sent", msgName.c_str(), teamMember);
}
else
nlwarning("command 'set_leader': unknown message named '%s'.", msgName.c_str());
*/
NLMISC::ICommand::execute("a setTeamLeader " + toString(peopleIndex), g_log);
}
}
}
};
REGISTER_ACTION_HANDLER( CHandlerSetTeamLeader, "set_team_leader");
//================================================================================================================= //=================================================================================================================
// Set a successor for the team // Set a successor for the team
@ -3236,6 +3310,12 @@ NLMISC_COMMAND(chatLog, "", "")
if (pIM->getLogState()) if (pIM->getLogState())
pIM->displaySystemInfo(CI18N::get("uiLogTurnedOn")); pIM->displaySystemInfo(CI18N::get("uiLogTurnedOn"));
CCDBNodeLeaf *node = pIM->getDbProp("UI:SAVE:CHATLOG_STATE", false);
if (node)
{
node->setValue32(pIM->getLogState() ? 1 : 0);
}
return true; return true;
}; };

@ -211,7 +211,8 @@ bool CPeopleList::sortExByOnline(const CPeople& a, const CPeople& b)
{ {
return (name_a < name_b); return (name_a < name_b);
} }
else { else
{
// Compare online status // Compare online status
switch (a.Online) switch (a.Online)
{ {
@ -467,14 +468,8 @@ void CPeopleList::displayLocalPlayerTell(const ucstring &receiver, uint index, c
return; return;
} }
ucstring cur_time; ucstring csr = CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw()) ? "(CSR) " : "";
CCDBNodeLeaf *pNL = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false); ucstring finalMsg = csr + CI18N::get("youTell") + ": " + msg;
if (pNL && pNL->getValueBool())
cur_time = CInterfaceManager::getTimestampHuman();
ucstring csr;
if (CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw())) csr += ucstring("(CSR) ");
ucstring finalMsg = cur_time + csr + CI18N::get("youTell") + ": " + msg;
// display msg with good color // display msg with good color
CInterfaceProperty prop; CInterfaceProperty prop;
prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," "); prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," ");
@ -783,10 +778,6 @@ void CPeopleList::setOnline(uint index, TCharConnectionState online)
_Peoples[index].Online = online; _Peoples[index].Online = online;
// If the people goes offline remove eventually opened chat
if (online == ccs_offline)
openCloseChat(index, false);
updatePeopleMenu(index); updatePeopleMenu(index);
} }
@ -944,14 +935,8 @@ class CHandlerContactEntry : public IActionHandler
ucstring final; ucstring final;
CChatWindow::encodeColorTag(prop.getRGBA(), final, false); CChatWindow::encodeColorTag(prop.getRGBA(), final, false);
ucstring cur_time; ucstring csr = CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw()) ? "(CSR) " : "";
CCDBNodeLeaf *pNL = CInterfaceManager::getInstance()->getDbProp("UI:SAVE:CHAT:SHOW_TIMES_IN_CHAT_CB", false); final += csr + CI18N::get("youTell")+": ";
if (pNL && pNL->getValueBool())
cur_time = CInterfaceManager::getTimestampHuman();
ucstring csr;
if (CHARACTER_TITLE::isCsrTitle(UserEntity->getTitleRaw())) csr += ucstring("(CSR) ");
final += cur_time + csr + CI18N::get("youTell")+": ";
prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," "); prop.readRGBA("UI:SAVE:CHAT:COLORS:TELL"," ");
CChatWindow::encodeColorTag(prop.getRGBA(), final, true); CChatWindow::encodeColorTag(prop.getRGBA(), final, true);
final += text; final += text;
@ -962,7 +947,6 @@ class CHandlerContactEntry : public IActionHandler
strFindReplace(final, CI18N::get("youTell"), s); strFindReplace(final, CI18N::get("youTell"), s);
CInterfaceManager::getInstance()->log(final); CInterfaceManager::getInstance()->log(final);
} }
} }
} }
}; };

@ -139,6 +139,7 @@ void CPlayerTrade::restoreItem(CDBCtrlSheet *exchangeSlot)
im.getBagItem(emptySlot).setWeight((uint32) exchangeSlot->getItemWeight()); im.getBagItem(emptySlot).setWeight((uint32) exchangeSlot->getItemWeight());
im.getBagItem(emptySlot).setNameId(exchangeSlot->getItemNameId()); im.getBagItem(emptySlot).setNameId(exchangeSlot->getItemNameId());
im.getBagItem(emptySlot).setInfoVersion(exchangeSlot->getItemInfoVersion()); im.getBagItem(emptySlot).setInfoVersion(exchangeSlot->getItemInfoVersion());
im.getBagItem(emptySlot).setResaleFlag(exchangeSlot->getItemResaleFlag());
} }

@ -1042,7 +1042,7 @@ void CSkillManager::setPlayerTitle(const std::string &name)
// *************************************************************************** // ***************************************************************************
// *************************************************************************** // ***************************************************************************
#define GROUP_TITLE_COMBO "ui:interface:info_player_skills:content:basics_skills:title:player_title" #define GROUP_TITLE_COMBO "ui:interface:info_player_skills:content:webinfos:title:player_title"
// *************************************************************************** // ***************************************************************************
class CHandlerTitleInit: public IActionHandler class CHandlerTitleInit: public IActionHandler

@ -70,6 +70,10 @@ public:
// from CInterfaceElement // from CInterfaceElement
virtual void visit(CInterfaceElementVisitor *visitor); virtual void visit(CInterfaceElementVisitor *visitor);
// special for mouse over : return true and fill the name of the cursor to display
virtual bool getMouseOverShape(std::string &/* texName */, uint8 &/* rot */, NLMISC::CRGBA &/* col */) { return false; }
}; };

@ -72,6 +72,8 @@ public:
bool getScale() const { return _Scale; } bool getScale() const { return _Scale; }
void setScale (bool s) { _Scale = s; } void setScale (bool s) { _Scale = s; }
bool getTile() const { return _Tile; }
void setTile (bool s) { _Tile = s; }
void setColor (const NLMISC::CRGBA &r) { _Color = r; } void setColor (const NLMISC::CRGBA &r) { _Color = r; }
// Reflected // Reflected

@ -42,5 +42,23 @@ void CViewLink::setHTMLView(CGroupHTML *html)
HTML = html; HTML = html;
} }
// ***************************************************************************
bool CViewLink::getMouseOverShape(string &texName, uint8 &rot, CRGBA &col)
{
if (HTML != NULL)
{
if (!LinkTitle.empty())
{
texName = LinkTitle;
rot= 0;
col = CRGBA::White;
return true;
}
}
return false;
}
// *************************************************************************** // ***************************************************************************

@ -38,8 +38,11 @@ public:
// The URI // The URI
std::string Link; std::string Link;
std::string LinkTitle;
// Set the main group // Set the main group
void setHTMLView(class CGroupHTML *html); void setHTMLView(class CGroupHTML *html);
bool getMouseOverShape(std::string &texName, uint8 &rot, NLMISC::CRGBA &col);
protected: protected:

@ -70,6 +70,7 @@ CViewPointer::CViewPointer (const TCtorParam &param)
_Color = CRGBA(255,255,255,255); _Color = CRGBA(255,255,255,255);
_LastHightLight = NULL; _LastHightLight = NULL;
_StringMode = false; _StringMode = false;
_ForceStringMode = false;
_StringCursor = NULL; _StringCursor = NULL;
} }
@ -255,6 +256,41 @@ void CViewPointer::draw ()
return; return;
} }
const vector<CViewBase *> &vUP = pIM->getViewsUnderPointer ();
for(uint i=0;i<vUP.size();i++)
{
CViewLink *vLink = dynamic_cast<CViewLink*>(vUP[i]);
if (vLink != NULL)
{
string tooltip;
uint8 rot;
if (vLink->getMouseOverShape(tooltip, rot, col))
{
setString(ucstring(tooltip));
sint32 texId = rVR.getTextureIdFromName ("curs_pick.tga");
CInterfaceGroup *stringCursor = IsMouseCursorHardware() ? _StringCursorHardware : _StringCursor;
if (stringCursor)
{
stringCursor->setX(_PointerX);
stringCursor->setY(_PointerY);
stringCursor->updateCoords();
stringCursor->draw();
// if in hardware mode, force to draw the default cursor no matter what..
if (IsMouseCursorHardware())
drawCursor(texId, col, 0);
}
else
{
drawCursor(texId, col, 0);
}
return;
}
}
}
// Draw if capture right // Draw if capture right
pCB = pIM->getCapturePointerRight(); pCB = pIM->getCapturePointerRight();
if (pCB != NULL) if (pCB != NULL)
@ -521,10 +557,43 @@ bool CViewPointer::drawPan(CCtrlBase* pCB, NLMISC::CRGBA col)
// -------------------------------------------------------------------------------------------------------------------- // --------------------------------------------------------------------------------------------------------------------
bool CViewPointer::drawCustom(CCtrlBase* pCB) bool CViewPointer::drawCustom(CCtrlBase* pCB)
{ {
std::string texName; string texName;
uint8 rot; uint8 rot;
NLMISC::CRGBA col; NLMISC::CRGBA col;
if (pCB->getMouseOverShape(texName, rot, col)) if (pCB->getMouseOverShape(texName, rot, col))
{
if (texName[0] == '@')
{
const string &tooltipInfos = texName.substr(1);
string tooltip;
vector<string> tooltipInfosList;
splitString(tooltipInfos, "@", tooltipInfosList);
texName = tooltipInfosList[0];
tooltip = tooltipInfosList[1];
nlinfo(tooltip.c_str());
setString(ucstring(tooltip));
CInterfaceManager *pIM = CInterfaceManager::getInstance();
CViewRenderer &rVR = pIM->getViewRenderer();
sint32 texId = rVR.getTextureIdFromName (texName);
CInterfaceGroup *stringCursor = IsMouseCursorHardware() ? _StringCursorHardware : _StringCursor;
if (stringCursor)
{
stringCursor->setX(_PointerX);
stringCursor->setY(_PointerY);
stringCursor->updateCoords();
stringCursor->draw();
// if in hardware mode, force to draw the default cursor no matter what..
if (IsMouseCursorHardware())
drawCursor(texId, col, 0);
}
else
{
drawCursor(texId, col, 0);
}
return true;
}
else
{ {
CInterfaceManager *pIM = CInterfaceManager::getInstance(); CInterfaceManager *pIM = CInterfaceManager::getInstance();
CViewRenderer &rVR = pIM->getViewRenderer(); CViewRenderer &rVR = pIM->getViewRenderer();
@ -532,6 +601,7 @@ bool CViewPointer::drawCustom(CCtrlBase* pCB)
drawCursor(texId, col, 0); drawCursor(texId, col, 0);
return true; return true;
} }
}
return false; return false;
} }

@ -153,6 +153,7 @@ private:
// Cursor mode // Cursor mode
bool _StringMode; bool _StringMode;
bool _ForceStringMode;
CInterfaceGroup *_StringCursor; CInterfaceGroup *_StringCursor;
CInterfaceGroup *_StringCursorHardware; CInterfaceGroup *_StringCursorHardware;
ucstring _ContextString; ucstring _ContextString;

@ -743,8 +743,8 @@ void CViewRenderer::loadTextures (const std::string &textureFileName, const std:
image.UVMin.V = uvMinV; image.UVMin.V = uvMinV;
image.UVMax.U = uvMaxU; image.UVMax.U = uvMaxU;
image.UVMax.V = uvMaxV; image.UVMax.V = uvMaxV;
sTGAname = tgaName; sTGAname = toLower(string(tgaName));
sTGAname = toLower(sTGAname);
string::size_type stripPng = sTGAname.find(".png"); string::size_type stripPng = sTGAname.find(".png");
if (stripPng != string::npos) if (stripPng != string::npos)
{ {
@ -752,6 +752,7 @@ void CViewRenderer::loadTextures (const std::string &textureFileName, const std:
sTGAname[stripPng + 2] = 'g'; sTGAname[stripPng + 2] = 'g';
sTGAname[stripPng + 3] = 'a'; sTGAname[stripPng + 3] = 'a';
} }
image.Name = sTGAname; image.Name = sTGAname;
image.GlobalTexturePtr = &(_GlobalTextures.back()); image.GlobalTexturePtr = &(_GlobalTextures.back());
if (getTextureIdFromName(sTGAname) != -1) if (getTextureIdFromName(sTGAname) != -1)
@ -1029,6 +1030,7 @@ sint32 CViewRenderer::getTextureIdFromName (const string &sName) const
// convert to lowCase // convert to lowCase
string nameLwr = toLower(sName); string nameLwr = toLower(sName);
string::size_type stripPng = nameLwr.find(".png"); string::size_type stripPng = nameLwr.find(".png");
if (stripPng != string::npos) if (stripPng != string::npos)
{ {
@ -1531,6 +1533,7 @@ void CViewRenderer::initSystemTextures()
addSystemTexture(RegenTexture, "regen.tga"); addSystemTexture(RegenTexture, "regen.tga");
addSystemTexture(RegenBackTexture, "regen_back.tga"); addSystemTexture(RegenBackTexture, "regen_back.tga");
addSystemTexture(GlowStarTexture, "glow_star_24.tga"); addSystemTexture(GlowStarTexture, "glow_star_24.tga");
addSystemTexture(ItemLockedByOwnerTexture, "r2ed_toolbar_lock_small.tga");
} }

@ -75,6 +75,7 @@ public:
RegenTexture, RegenTexture,
RegenBackTexture, RegenBackTexture,
GlowStarTexture, GlowStarTexture,
ItemLockedByOwnerTexture,
NumSystemTextures, NumSystemTextures,
}; };

@ -225,7 +225,10 @@ HTAttr p_attr[] =
HTAttr div_attr[] = HTAttr div_attr[] =
{ {
HTML_ATTR(DIV,CLASS),
HTML_ATTR(DIV,ID),
HTML_ATTR(DIV,NAME), HTML_ATTR(DIV,NAME),
HTML_ATTR(DIV,STYLE),
{ 0 } { 0 }
}; };
@ -535,6 +538,7 @@ const std::string &setCurrentDomain(const std::string &url)
return HTTPCurrentDomain; return HTTPCurrentDomain;
} }
void initLibWWW() void initLibWWW()
{ {
static bool initialized = false; static bool initialized = false;

@ -206,7 +206,10 @@ enum
enum enum
{ {
HTML_ATTR(DIV,NAME) = 0, HTML_ATTR(DIV,CLASS) = 0,
HTML_ATTR(DIV,ID),
HTML_ATTR(DIV,NAME),
HTML_ATTR(DIV,STYLE),
}; };

@ -738,8 +738,10 @@ void initLoginScreen()
if(!l.empty()) if(!l.empty())
{ {
CGroupEditBox *pGEB = dynamic_cast<CGroupEditBox*>(pIM->getElementFromId(CTRL_EDITBOX_LOGIN)); CGroupEditBox *pGEB = dynamic_cast<CGroupEditBox*>(pIM->getElementFromId(CTRL_EDITBOX_LOGIN));
if (pGEB != NULL) if (pGEB != NULL && (pGEB->getInputString().empty()))
{
pGEB->setInputString(l); pGEB->setInputString(l);
}
pIM->runActionHandler("set_keyboard_focus", NULL, "target=" CTRL_EDITBOX_PASSWORD "|select_all=false"); pIM->runActionHandler("set_keyboard_focus", NULL, "target=" CTRL_EDITBOX_PASSWORD "|select_all=false");
} }
else else
@ -1792,7 +1794,6 @@ class CAHOpenURL : public IActionHandler
} }
else else
{ {
DWORD ret = 0;
LPVOID lpMsgBuf; LPVOID lpMsgBuf;
FormatMessage( FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_ALLOCATE_BUFFER |

@ -2889,6 +2889,7 @@ bool mainLoop()
// This code must remain at the very end of the main loop. // This code must remain at the very end of the main loop.
if(LoginSM.getCurrentState() == CLoginStateMachine::st_enter_far_tp_main_loop) if(LoginSM.getCurrentState() == CLoginStateMachine::st_enter_far_tp_main_loop)
{ {
CInterfaceManager::getInstance()->executeLuaScript("game:onFarTpStart()");
// Will loop the network until the end of the relogging process // Will loop the network until the end of the relogging process
FarTP.farTPmainLoop(); FarTP.farTPmainLoop();
@ -2965,6 +2966,8 @@ bool mainLoop()
// Get the Connection State (must be done after any Far TP to prevent the uiDisconnected box to be displayed) // Get the Connection State (must be done after any Far TP to prevent the uiDisconnected box to be displayed)
lastConnectionState = CNetworkConnection::Connected; lastConnectionState = CNetworkConnection::Connected;
connectionState = NetMngr.getConnectionState(); connectionState = NetMngr.getConnectionState();
CInterfaceManager::getInstance()->executeLuaScript("game:onFarTpEnd()");
} }
} // end of main loop } // end of main loop

@ -664,10 +664,12 @@ void CInterfaceChatDisplayer::displayChat(TDataSetIndex compressedSenderIndex, c
} }
// select DB // select DB
sint32 dbIndex = ChatMngr.getDynamicChannelDbIndexFromId(dynChatId);
clamp(dbIndex,0 , CChatGroup::MaxDynChanPerPlayer);
string entry="UI:SAVE:CHAT:COLORS:"; string entry="UI:SAVE:CHAT:COLORS:";
switch(mode) switch(mode)
{ {
case CChatGroup::dyn_chat: entry+="DYN"; break; case CChatGroup::dyn_chat: entry+="DYN:" + NLMISC::toString(dbIndex); break;
case CChatGroup::say: entry+="SAY"; break; case CChatGroup::say: entry+="SAY"; break;
case CChatGroup::shout: entry+="SHOUT"; break; case CChatGroup::shout: entry+="SHOUT"; break;
case CChatGroup::team: entry+="GROUP"; break; case CChatGroup::team: entry+="GROUP"; break;
@ -697,6 +699,11 @@ void CInterfaceChatDisplayer::displayChat(TDataSetIndex compressedSenderIndex, c
} }
} }
if (stringCategory == "emt")
{
bubbleWanted = false;
}
if (mode != CChatGroup::system) if (mode != CChatGroup::system)
{ {
// find the sender/text separator to put color tags // find the sender/text separator to put color tags
@ -3206,7 +3213,7 @@ void impulseOutpostDeclareWarAck(NLMISC::CBitMemStream &impulse)
node->setValue32(timeStartAttack); node->setValue32(timeStartAttack);
} }
extern void addWebIGParams (string &url); extern void addWebIGParams(string &url, bool trustedDomain);
//----------------------------------------------- //-----------------------------------------------
//----------------------------------------------- //-----------------------------------------------
@ -3290,7 +3297,6 @@ private:
string group = titleStr.toString(); string group = titleStr.toString();
// <missing:XXX> // <missing:XXX>
group = group.substr(9, group.size()-10); group = group.substr(9, group.size()-10);
nlinfo("group = %s", group.c_str());
groupHtml = dynamic_cast<CGroupHTML*>(pIM->getElementFromId("ui:interface:"+group+":content:html")); groupHtml = dynamic_cast<CGroupHTML*>(pIM->getElementFromId("ui:interface:"+group+":content:html"));
if (!groupHtml) if (!groupHtml)
{ {
@ -3312,7 +3318,7 @@ private:
if (group == "webig") if (group == "webig")
pGC->setActive(true); pGC->setActive(true);
string url = contentStr.toString(); string url = contentStr.toString();
addWebIGParams(url); addWebIGParams(url, true);
groupHtml->browse(url.c_str()); groupHtml->browse(url.c_str());
pIM->setTopWindow(pGC); pIM->setTopWindow(pGC);
} }

@ -164,7 +164,7 @@ bool CPlayerCL::isNeutral() const
//----------------------------------------------- //-----------------------------------------------
bool CPlayerCL::isFriend () const bool CPlayerCL::isFriend () const
{ {
return isNeutral() || isNeutralPVP() || isAlly(); return isNeutral() || isAlly();
} }
@ -174,6 +174,14 @@ bool CPlayerCL::isFriend () const
//----------------------------------------------- //-----------------------------------------------
bool CPlayerCL::isEnemy () const bool CPlayerCL::isEnemy () const
{ {
// Challenge i.e. SOLO FULL PVP
if( getPvpMode()&PVP_MODE::PvpChallenge ||
UserEntity->getPvpMode()&PVP_MODE::PvpChallenge )
{
return true;
}
// if one of 2 players is not in pvp they can't be enemies // if one of 2 players is not in pvp they can't be enemies
if( UserEntity->getPvpMode() == PVP_MODE::None || if( UserEntity->getPvpMode() == PVP_MODE::None ||
getPvpMode() == PVP_MODE::None ) getPvpMode() == PVP_MODE::None )
@ -181,17 +189,33 @@ bool CPlayerCL::isEnemy () const
return false; return false;
} }
// Outpost // if one of 2 players is safe they can't be enemies
if ( isAnOutpostEnemy() ) if( UserEntity->getPvpMode()&PVP_MODE::PvpSafe ||
getPvpMode()&PVP_MODE::PvpSafe )
{ {
return true; return false;
} }
// Challenge // if one of 2 players are in safe zone and not flagged they can't be enemies
if( getPvpMode()&PVP_MODE::PvpChallenge && if ((UserEntity->getPvpMode()&PVP_MODE::PvpZoneSafe &&
UserEntity->getPvpMode()&PVP_MODE::PvpChallenge ) ((UserEntity->getPvpMode()&PVP_MODE::PvpFactionFlagged) == 0))
||
(getPvpMode()&PVP_MODE::PvpZoneSafe &&
((getPvpMode()&PVP_MODE::PvpFactionFlagged) == 0)))
{
return false;
}
// Duel
if( getPvpMode()&PVP_MODE::PvpDuel &&
UserEntity->getPvpMode()&PVP_MODE::PvpDuel )
{
return true; // TODO
}
// Outpost
if ( isAnOutpostEnemy() )
{ {
if( !isInTeam() )
return true; return true;
} }
@ -199,7 +223,8 @@ bool CPlayerCL::isEnemy () const
if( getPvpMode()&PVP_MODE::PvpZoneFree && if( getPvpMode()&PVP_MODE::PvpZoneFree &&
UserEntity->getPvpMode()&PVP_MODE::PvpZoneFree ) UserEntity->getPvpMode()&PVP_MODE::PvpZoneFree )
{ {
if( !isInTeam() && !isInGuild() ) // If not in same Team and not in same League => ennemy
if( !isInTeam() && !isInSameLeague() )
return true; return true;
} }
@ -207,7 +232,11 @@ bool CPlayerCL::isEnemy () const
if( getPvpMode()&PVP_MODE::PvpZoneGuild && if( getPvpMode()&PVP_MODE::PvpZoneGuild &&
UserEntity->getPvpMode()&PVP_MODE::PvpZoneGuild ) UserEntity->getPvpMode()&PVP_MODE::PvpZoneGuild )
{ {
if( !isInTeam() && !isInGuild() ) // If in same Guild but different Leagues => ennemy
if ( isInSameGuild() && oneInLeague() && !isInSameLeague() )
return true;
if( !isInTeam() && !isInSameLeague() )
return true; return true;
} }
@ -219,29 +248,18 @@ bool CPlayerCL::isEnemy () const
return true; return true;
} }
// Duel // Free PVP : Ennemis are not in team AND not in league
if( getPvpMode()&PVP_MODE::PvpDuel &&
UserEntity->getPvpMode()&PVP_MODE::PvpDuel )
{
return true; // TODO
}
// Faction
if ((getPvpMode()&PVP_MODE::PvpFaction || getPvpMode()&PVP_MODE::PvpFactionFlagged) && if ((getPvpMode()&PVP_MODE::PvpFaction || getPvpMode()&PVP_MODE::PvpFactionFlagged) &&
(UserEntity->getPvpMode()&PVP_MODE::PvpFaction || UserEntity->getPvpMode()&PVP_MODE::PvpFactionFlagged)) (UserEntity->getPvpMode()&PVP_MODE::PvpFaction || UserEntity->getPvpMode()&PVP_MODE::PvpFactionFlagged))
{ {
// Check if is not ally // If in same Guild but different Leagues => ennemy
if (!isInTeam() && !isInGuild()) if ( isInSameGuild() && oneInLeague() && !isInSameLeague() )
{
// Check for each Clan if is in opposition
for (uint8 i = 0; i < PVP_CLAN::NbClans; i++)
{
if ((isPvpEnnemy(i) && UserEntity->isPvpAlly(i)) || (isPvpAlly(i) && UserEntity->isPvpEnnemy(i)))
return true; return true;
}
}
if (!isInTeam() && !isInSameLeague())
return true;
} }
return false; return false;
} // isEnemy // } // isEnemy //
@ -253,24 +271,30 @@ bool CPlayerCL::isEnemy () const
//----------------------------------------------- //-----------------------------------------------
bool CPlayerCL::isAlly() const bool CPlayerCL::isAlly() const
{ {
// if one of 2 players is not in pvp they can't be enemies
// Challenge i.e. SOLO FULL PVP
if( getPvpMode()&PVP_MODE::PvpChallenge ||
UserEntity->getPvpMode()&PVP_MODE::PvpChallenge )
{
return false;
}
// if one of 2 players is not in pvp they can't be allies
if( UserEntity->getPvpMode() == PVP_MODE::None || if( UserEntity->getPvpMode() == PVP_MODE::None ||
getPvpMode() == PVP_MODE::None ) getPvpMode() == PVP_MODE::None )
{ {
return false; return false;
} }
// Outpost // if one of 2 players is in safe zone and not other they can't be allies
if ( isAnOutpostAlly() ) if ((UserEntity->getPvpMode()&PVP_MODE::PvpSafe) != (getPvpMode()&PVP_MODE::PvpSafe))
{ {
return true; return false;
} }
// Challenge // Outpost
if( getPvpMode()&PVP_MODE::PvpChallenge && if ( isAnOutpostAlly() )
UserEntity->getPvpMode()&PVP_MODE::PvpChallenge )
{ {
if( isInTeam() )
return true; return true;
} }
@ -278,7 +302,7 @@ bool CPlayerCL::isAlly() const
if( getPvpMode()&PVP_MODE::PvpZoneFree && if( getPvpMode()&PVP_MODE::PvpZoneFree &&
UserEntity->getPvpMode()&PVP_MODE::PvpZoneFree ) UserEntity->getPvpMode()&PVP_MODE::PvpZoneFree )
{ {
if( isInTeam() || isInGuild() ) if( isInTeam() || isInSameLeague() )
return true; return true;
} }
@ -286,8 +310,12 @@ bool CPlayerCL::isAlly() const
if( getPvpMode()&PVP_MODE::PvpZoneGuild && if( getPvpMode()&PVP_MODE::PvpZoneGuild &&
UserEntity->getPvpMode()&PVP_MODE::PvpZoneGuild ) UserEntity->getPvpMode()&PVP_MODE::PvpZoneGuild )
{ {
if( isInTeam() || isInGuild() ) if( isInTeam() || isInSameLeague() )
return true;
if ( isInSameGuild() && !oneInLeague() )
return true; return true;
} }
// Zone Faction // Zone Faction
@ -298,27 +326,16 @@ bool CPlayerCL::isAlly() const
return true; return true;
} }
// Faction // Free PVP : Allies are in team OR in league
if ((getPvpMode()&PVP_MODE::PvpFaction || getPvpMode()&PVP_MODE::PvpFactionFlagged) && if ((getPvpMode()&PVP_MODE::PvpFaction || getPvpMode()&PVP_MODE::PvpFactionFlagged) &&
(UserEntity->getPvpMode()&PVP_MODE::PvpFaction || UserEntity->getPvpMode()&PVP_MODE::PvpFactionFlagged)) (UserEntity->getPvpMode()&PVP_MODE::PvpFaction || UserEntity->getPvpMode()&PVP_MODE::PvpFactionFlagged))
{ {
if (isInTeam() && isInGuild()) if (isInTeam() || isInSameLeague())
return true; return true;
// Check for each Clan if is in opposition if ( isInSameGuild() && !oneInLeague() )
for (uint8 i = 0; i < PVP_CLAN::NbClans; i++)
{
if ((isPvpEnnemy(i) && UserEntity->isPvpAlly(i)) || (isPvpAlly(i) && UserEntity->isPvpEnnemy(i)))
return false;
}
// Check for each Clan if is in same clan
for (uint8 i = 0; i < PVP_CLAN::NbClans; i++)
{
if ((isPvpEnnemy(i) && UserEntity->isPvpEnnemy(i)) || (isPvpAlly(i) && UserEntity->isPvpAlly(i)))
return true; return true;
} }
}
return false; return false;
@ -336,66 +353,12 @@ bool CPlayerCL::isNeutralPVP() const
return false; return false;
} }
// Outpost if( UserEntity->getPvpMode() == PVP_MODE::None )
if ( getOutpostId() != 0 )
{
if( UserEntity->getOutpostId() != getOutpostId() )
{
return true;
}
}
// Challenge
if( getPvpMode()&PVP_MODE::PvpChallenge &&
!(UserEntity->getPvpMode()&PVP_MODE::PvpChallenge) )
{
return true;
}
// Zone Free
if( getPvpMode()&PVP_MODE::PvpZoneFree &&
!(UserEntity->getPvpMode()&PVP_MODE::PvpZoneFree) )
{
return true;
}
// Zone Guild
if( getPvpMode()&PVP_MODE::PvpZoneGuild &&
!(UserEntity->getPvpMode()&PVP_MODE::PvpZoneGuild) )
{
return true;
}
// Zone Faction
if( getPvpMode()&PVP_MODE::PvpZoneFaction &&
!(UserEntity->getPvpMode()&PVP_MODE::PvpZoneFaction) )
{
return true;
}
// Duel
if( getPvpMode()&PVP_MODE::PvpDuel &&
!(UserEntity->getPvpMode()&PVP_MODE::PvpDuel) )
{ {
return true;
}
if ((getPvpMode()&PVP_MODE::PvpFaction || getPvpMode()&PVP_MODE::PvpFactionFlagged) &&
(UserEntity->getPvpMode()&PVP_MODE::PvpFaction || UserEntity->getPvpMode()&PVP_MODE::PvpFactionFlagged))
{
// Check for each Clan if is in opposition or same
for (uint8 i = 0; i < PVP_CLAN::NbClans; i++)
{
if ((isPvpEnnemy(i) && UserEntity->isPvpAlly(i)) ||
(isPvpAlly(i) && UserEntity->isPvpEnnemy(i)) ||
(isPvpEnnemy(i) && UserEntity->isPvpEnnemy(i)) ||
(isPvpAlly(i) && UserEntity->isPvpAlly(i)))
return false; return false;
} }
return true;
}
return false; return (!isEnemy() && !isAlly());
} }

@ -34,6 +34,8 @@ namespace STRING_MANAGER
// *************************************************************************** // ***************************************************************************
map<string, CStringManagerClient::CItem> CStringManagerClient::_SpecItem_TempMap; map<string, CStringManagerClient::CItem> CStringManagerClient::_SpecItem_TempMap;
map<ucstring, ucstring> CStringManagerClient::_DynStrings;
vector<ucstring> CStringManagerClient::_TitleWords;
bool CStringManagerClient::_SpecItem_MemoryCompressed = false; bool CStringManagerClient::_SpecItem_MemoryCompressed = false;
char *CStringManagerClient::_SpecItem_Labels = NULL; char *CStringManagerClient::_SpecItem_Labels = NULL;
ucchar *CStringManagerClient::_SpecItem_NameDesc = NULL; ucchar *CStringManagerClient::_SpecItem_NameDesc = NULL;
@ -381,7 +383,15 @@ restartLoop4:
result = ucstring(tmp) + it->second; result = ucstring(tmp) + it->second;
} }
else else
{
result = it->second; result = it->second;
if (result.size() > 9 && result.substr(0, 9) == ucstring("<missing:"))
{
map<ucstring, ucstring>::iterator itds = _DynStrings.find(result.substr(9, result.size()-10));
if (itds != _DynStrings.end())
result = itds->second;
}
}
} }
return true; return true;
@ -1595,9 +1605,29 @@ const ucchar *CStringManagerClient::getSPhraseLocalizedDescription(NLMISC::CShee
// *************************************************************************** // ***************************************************************************
const ucchar *CStringManagerClient::getTitleLocalizedName(const std::string &titleId, bool women) const ucchar *CStringManagerClient::getTitleLocalizedName(const std::string &titleId, bool women)
{ {
return getSpecialWord(titleId,women); const ucchar * infos = getSpecialWord(titleId, women);
ucstring infosUC(infos);
vector<ucstring> listInfos;
splitUCString(infosUC, ucstring("#"), listInfos);
if (listInfos.empty())
return infos;
_TitleWords.push_back(listInfos[0]);
return _TitleWords.back().c_str();
}
vector<ucstring> CStringManagerClient::getTitleInfos(const std::string &titleId, bool women)
{
const ucchar * infos = getSpecialWord(titleId, women);
ucstring infosUC(infos);
vector<ucstring> listInfos;
splitUCString(infosUC, ucstring("#"), listInfos);
return listInfos;
} }
// *************************************************************************** // ***************************************************************************
const ucchar *CStringManagerClient::getClassificationTypeLocalizedName(EGSPD::CClassificationType::TClassificationType type) const ucchar *CStringManagerClient::getClassificationTypeLocalizedName(EGSPD::CClassificationType::TClassificationType type)
{ {
@ -1640,6 +1670,13 @@ const ucchar *CStringManagerClient::getSquadLocalizedDescription(NLMISC::CSheetI
return getSpecialDesc(id.toString()); return getSpecialDesc(id.toString());
} }
// ***************************************************************************
void CStringManagerClient::replaceDynString(const ucstring &name, const ucstring &text)
{
_DynStrings[name] = text;
}
// *************************************************************************** // ***************************************************************************
void CStringManagerClient::replaceSBrickName(NLMISC::CSheetId id, const ucstring &name, const ucstring &desc, const ucstring &desc2) void CStringManagerClient::replaceSBrickName(NLMISC::CSheetId id, const ucstring &name, const ucstring &desc, const ucstring &desc2)
{ {

@ -77,6 +77,7 @@ public:
static void specialWordsMemoryCompress(); static void specialWordsMemoryCompress();
// Yoyo: Replace the Brick Name with Filled stats (CSBrickManager work). No-Op if not found // Yoyo: Replace the Brick Name with Filled stats (CSBrickManager work). No-Op if not found
static void replaceSBrickName(NLMISC::CSheetId id, const ucstring &name, const ucstring &desc, const ucstring &desc2); static void replaceSBrickName(NLMISC::CSheetId id, const ucstring &name, const ucstring &desc, const ucstring &desc2);
static void replaceDynString(const ucstring &name, const ucstring &text);
// Get the Localized Name of the Places. // Get the Localized Name of the Places.
static const ucchar *getPlaceLocalizedName(const std::string &placeNameID); static const ucchar *getPlaceLocalizedName(const std::string &placeNameID);
@ -106,6 +107,7 @@ public:
// Get the Localized Title name // Get the Localized Title name
static const ucchar *getTitleLocalizedName(const std::string &titleId, bool women); static const ucchar *getTitleLocalizedName(const std::string &titleId, bool women);
static std::vector<ucstring> CStringManagerClient::getTitleInfos(const std::string &titleId, bool women);
// Get the Localized name of a classification type // Get the Localized name of a classification type
static const ucchar *getClassificationTypeLocalizedName(EGSPD::CClassificationType::TClassificationType type); static const ucchar *getClassificationTypeLocalizedName(EGSPD::CClassificationType::TClassificationType type);
@ -215,8 +217,6 @@ private:
// Callback for dyn string value from the server // Callback for dyn string value from the server
TStringCallbacksContainer _DynStringsCallbacks; TStringCallbacksContainer _DynStringsCallbacks;
// Return value for waiting string.. // Return value for waiting string..
static ucstring _WaitString; static ucstring _WaitString;
@ -273,6 +273,9 @@ private:
static bool _SpecItem_MemoryCompressed; static bool _SpecItem_MemoryCompressed;
static std::map<std::string, CItem> _SpecItem_TempMap; static std::map<std::string, CItem> _SpecItem_TempMap;
static std::vector<ucstring> _TitleWords;
static std::map<ucstring, ucstring> _DynStrings;
static char *_SpecItem_Labels; static char *_SpecItem_Labels;
static ucchar *_SpecItem_NameDesc; static ucchar *_SpecItem_NameDesc;

@ -507,7 +507,7 @@ void CUserEntity::updateVisualPropertyName(const NLMISC::TGameCycle &gameCycle,
CPlayerCL::updateVisualPropertyName(gameCycle, prop); CPlayerCL::updateVisualPropertyName(gameCycle, prop);
// Name changed ? // Name changed ?
if (oldNameId != _NameId) /* if (oldNameId != _NameId)
{ {
CInterfaceManager *pIM = CInterfaceManager::getInstance(); CInterfaceManager *pIM = CInterfaceManager::getInstance();
CInterfaceElement *element = pIM->getElementFromId("ui:interface:mailbox:content:html"); CInterfaceElement *element = pIM->getElementFromId("ui:interface:mailbox:content:html");
@ -518,7 +518,7 @@ void CUserEntity::updateVisualPropertyName(const NLMISC::TGameCycle &gameCycle,
html->browse("home"); html->browse("home");
} }
} }
*/
}// updateVisualPropertyName // }// updateVisualPropertyName //
//----------------------------------------------- //-----------------------------------------------
@ -2657,36 +2657,39 @@ void CUserEntity::selection(const CLFECOMMON::TCLEntityId &slot) // virtual
playerGiftNeeded->setValue32(0); playerGiftNeeded->setValue32(0);
} }
} }
/* TODO ULU : Add RP tags */
// update pvp tags // update pvp tags
CViewBase * tagView = dynamic_cast<CViewBase*>(pIM->getElementFromId("ui:interface:target:pvp_tags"));
CViewBase * contentView = dynamic_cast<CViewBase*>(pIM->getElementFromId("ui:interface:target:content"));
if ((tgtSlot!=CLFECOMMON::INVALID_SLOT) && entity) if ((tgtSlot!=CLFECOMMON::INVALID_SLOT) && entity)
{ {
CPlayerCL *pPlayer = dynamic_cast<CPlayerCL*>(entity); CPlayerCL *pPlayer = dynamic_cast<CPlayerCL*>(entity);
if (pPlayer) if (pPlayer)
{ {
for (uint8 i = 0; i < 7; i++) /*// Pvp Mode
{ CViewBitmap * tagMode = dynamic_cast<CViewBitmap*>(pIM->getElementFromId("ui:interface:target:pvp_tags:mode"));
CViewBitmap * tag = dynamic_cast<CViewBitmap*>(pIM->getElementFromId("ui:interface:target:pvp_tags:tag_"+toString(i))); if (tagMode)
if (tag)
{ {
if ((pPlayer->getPvpMode()&PVP_MODE::PvpFaction || pPlayer->getPvpMode()&PVP_MODE::PvpFactionFlagged) && pPlayer->isPvpAlly(i)) if (pPlayer->getPvpMode()&PVP_MODE::PvpFaction)
{ tagMode->setTexture("pvp_orange.tga");
tag->setTexture("pvp_ally_"+toString(i)+".tga"); else if (pPlayer->getPvpMode()&PVP_MODE::PvpFactionFlagged)
} tagMode->setTexture("pvp_red.tga");
else if ((pPlayer->getPvpMode()&PVP_MODE::PvpFaction || pPlayer->getPvpMode()&PVP_MODE::PvpFactionFlagged) && pPlayer->isPvpEnnemy(i)) else
{ tagMode->setTexture("alpha_10.tga");
tag->setTexture("pvp_enemy_"+toString(i)+".tga");
} }
*/
/*// Pvp available actions (attack, heal, both)
CViewBitmap * tagMode = dynamic_cast<CViewBitmap*>(pIM->getElementFromId("ui:interface:target:pvp_tags:actions"));
if (tagMode)
{
if (pPlayer->getPvpMode()&PVP_MODE::PvpFaction)
tag->setTexture("pvp_orange.tga");
else if (pPlayer->getPvpMode()&PVP_MODE::PvpFactionFlagged)
tag->setTexture("pvp_red.tga");
else else
{
tag->setTexture("alpha_10.tga"); tag->setTexture("alpha_10.tga");
} }*/
}
}
} }
} }

@ -477,6 +477,14 @@ public:
/// true if current behaviour allows to change front /// true if current behaviour allows to change front
bool canChangeFront(); bool canChangeFront();
ucstring getLoginName()
{
if (_LoginName == ucstring(""))
_LoginName = getDisplayName();
return _LoginName;
}
protected: protected:
class CSpeedFactor : public ICDBNode::IPropertyObserver class CSpeedFactor : public ICDBNode::IPropertyObserver
{ {
@ -741,6 +749,8 @@ private:
/// previous items in hand before they have been changed by an auto-equip due to an action (ex: forage) /// previous items in hand before they have been changed by an auto-equip due to an action (ex: forage)
CItemSnapshot _PreviousRightHandItem; CItemSnapshot _PreviousRightHandItem;
CItemSnapshot _PreviousLeftHandItem; CItemSnapshot _PreviousLeftHandItem;
ucstring _LoginName;
}; };
/// Out game received position /// Out game received position

Loading…
Cancel
Save