Jump to content
  • Announcements

    • Xmat

      Pravidlo pro postování v TTT

      Do sekce Tipy, triky, tutoriály nepatří žádné dotazy.   Postujte sem vaše návody, tipy a různé další věci jež uznáte za vhodné sdělit zdejšímu osazenstvu, ale veškeré dotazy směřujte do sekce Všeobecná diskuse.
    • Replik

      Seznam návodů a důležitých témat v této sekci

      Pro lepší přehlednost jsem vytvořil tento seznam, který vás, méně zkušené, lépe provede touto sekcí. Věřím, že zde najdete, co hledáte. Vypsané jsou návody, které jsou oficiálně uznané jako návody. Běžné diskuze, které neposkytují postupy a rady zvěřejněny nejsou.   Instalace vlastního MaNGOS Serveru Díky těmto návodům budete (měli by jste být) schopni vytvořit a následně spustit váš vlastní server. Nastavení je pro verze s i bez datadisku.   Instalace MaNGOS Serveru (bez datadisku TBC) - Autor Benny Instalace MaNGOS Serveru (s datadiskem TBC) - Autor Malfik Instalace MaNGOS Serveru v prostředí Linux - Autor charlie Instalace MaNGOS Serveru v prostředí Linux - Autor kupkoid   Chyby a jejich řešení při přihlašování k serveru - Autor Cybe   Zálohování uživatelských dat   Dávkový soubor (BAT soubor) pro vytvoření SQL záloh - Autor Replik   Kompilování - tvoření vlastních release (revizí)   Tvorba kompilací pro Win32 (MangoScript) - Autor bLuma   Ostatní - těžko zařaditelné, ale neznamená to, že nejsou dobré   VIP Systém - Autor charlie Tvorba Webových stránek pro MaNGOS - Autor zahuba Tvorba teleportačních NPC (MangoScript) - Autor Replik Registrační web (původně předělaná SPORA) Funkční pro Antrix i MaNGOS - Autor Replik Nastavení a spuštění Minimanager pro MaNGOS - Autor BlackMartin Nastavení MaNGOS Website - Autor Artorius   Samozřejmě jsou zde i jiné návody, ale tyto jsou nejvíce používané, proto věřím, že vám budou nápomocné. Tuto sekci budeme upravovat podle potřeby. Pokud by jste něco nenašli nebo si nevěděli rady, hledejte na fóru a teprve potom založte vlastní topik. Pokud nějaký autor vytvoří kvalitní návod a chtěl by ho zveřejnit i v tomto seznamu, doporučuji, aby mi napsal zprávu skrze PM.   Díky a přeji hezký den na WoWResource   Replik
    • Aristo

      Příspěvky tam, kde nemají co dělat

      Dodržujte zákaz přispívání do topiků s repaky pokud si to zakladatelé nepřejí!! Opakované psaní příspěvků bude trestáno warnem.
    • Aristo

      Používání spoilerů

      Poslední dobou má většina uživatelů fora zvláštní nutkání postovat extrémně dlouhé texty nebo kódy, které zabírají v nejedenom případu i 80% obsahu celé stránky a hodně tak zvedají nepřehlednost v topiku. Chtěl bych všechny uživatele požádat, aby při postování citací, jakýchkoliv kódů, errorů, atp... delších než 30 řádků používali funkci spoileru.   Funkci vyvoláte příkazem [spoiler] text [/spoiler]   Ukázka:  
Sign in to follow this  
Wolf Officious

[Patch] AutoBroadcast

Recommended Posts

Původně napsáno pro: MaNGOS 9799

Testováno na revizi: 9799 (po úpravě poběží i na starších revizích)

Jestli bude zájem upravím to pro starší revize. (Jde jen o to, že WUPDATE_COUNT a m_timers[WUPDATE_AUTOBROADCAST].. se píšou na stejný místa ale nedají se najít podle indícií, které jsou zde popsané. Zkušenný patcher to se základními znalostmi C++ jistě zvládne sám.)

 

######################################################################

#### AUTOBROADCAST PATCH VČETNĚ UKLÁDÁNÍ NAPOSLEDY POSTNUTÝCH ABR ####

######################################################################

 

A je to tady. Autobroadcast, který jsem upravil k obrazu svému. Opět nevím kdo to původně napsal, ale čert to vem :diablo:, moc z toho stejně nezbylo.

 

Vždycky mě štvalo, že AutoBroadcast po restartu začal zas od začátku. Vyřešil jsem to ukládáním hodnoty do databáze jako autobroadcast ID 0, kam se ukládá se hodnota `next` z naposledy postnutého Broadcastu do worldu. Po restartu se čte hodnota `next` z tabulky `autobroadcast` ID 0.

 

POZOR: Nedoporučuji používat na více worldech, které jedou přes jeden realm list (login, chcete-li). Ovšem když si s tím pohrajete, například že AutoBroadcasty budou uložené v databázi jednotlivých worldů, neměl by být problém.

 

Některé řádky obsahují poznámku // ABR WLK. Ve zdrojáku dělám dohledatelné značky, aby hned bez složitého zkoumání bylo jasné, co k čemu patří.

 

Doporučuji zálohovat tabulku `mangos_string` z databáze worldu a celou databázi ralmů (login, chcete-li tomu tak říkat) před provedením SQL! Jelikož patche provádím ručně, opět to rozepíšu:

 

1. SQL side

-- A: (WORLD databáze):

DELETE FROM `mangos_string` WHERE `entry` = 1300;
INSERT INTO `mangos_string`(`entry`,`content_default`,`content_loc1`,`content_loc2`,`content_loc3`,`content_loc4`,`content_loc5`,`content_loc6`,`content_loc7`,`content_loc8`) VALUES
(1300,'|cff0000ee[Zpráva Serveru]: |cffcc00ff%s|r',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL);

-- B: (REALM (login) databáze):

CREATE TABLE `autobroadcast` (
 `id` int(11) NOT NULL,
 `text` longtext NOT NULL,
 `next` int(11) NOT NULL DEFAULT '1',
 PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;

insert  into `autobroadcast`(`id`,`text`,`next`) values
(0,'last nextid',1),
(1,'AutoBroadcast - testovaci zprava 1, nasleduje 2.',2),
(2,'AutoBroadcast - testovaci zprava 2, nasleduje 3.',3),
(3,'AutoBroadcast - testovaci zprava 3, nasleduje 4.',4),
(4,'AutoBroadcast - testovaci zprava 4, nasleduje 5.',5),
(5,'AutoBroadcast - testovaci zprava 5, nasleduje 1.',1);

 

 

(POZNÁMKA: Když je před řádkou znaménko "+", označuje to, že tuhle řádku je třeba přidat.

############ Ovšem bez toho + na začátku. Když je na záčátku "-" (mínus), řádek smažte.)

 

2. CORE side - SOUBOR src/game/Language.h NAJDI ŘÁDEK // FREE IDS

+    LANG_AUTO_BROADCAST                 = 1300,

 

 

3. CORE side - SOUBOR src/game/World.cpp

-- A: NAJDI ŘÁDEK #include "BattleGroundMgr.h"

+#include "Language.h" // ABR WLK

-- B: NAJDI ŘÁDEK realmID, uint64(m_startTime), isoDate);

+    static uint32 abtimer;                                       // ABR WLK
+    abtimer = sConfig.GetIntDefault("AutoBroadcast.Timer", 20);      // ABR WLK

-- C: NAJDI ŘÁDEK m_timers[WUPDATE_DELETECHARS].SetInterval(DAY*IN_MILLISECONDS); // check for chars to delete every day

+    m_timers[WUPDATE_AUTOBROADCAST].SetInterval(abtimer*MINUTE*IN_MILLISECONDS); // ABR WLK

-- D: NAJDI ŘÁDKY:

///- Process Game events when necessary
   if (m_timers[WUPDATE_EVENTS].Passed())
   {
       m_timers[WUPDATE_EVENTS].Reset();                   // to give time for Update() to be processed
       uint32 nextGameEvent = sGameEventMgr.Update();
       m_timers[WUPDATE_EVENTS].SetInterval(nextGameEvent);
       m_timers[WUPDATE_EVENTS].Reset();
   }

-- ..A HNED ZA NĚ PŘIDEJ NÁSLEDUJÍCÍ:

+    static uint32 autobroadcaston;   // ABR WLK begin
+    autobroadcaston = sConfig.GetIntDefault("AutoBroadcast.On", 1);
+    if(autobroadcaston == 1)
+    {
+        if (m_timers[WUPDATE_AUTOBROADCAST].Passed())
+        {
+            m_timers[WUPDATE_AUTOBROADCAST].Reset();
+            SendBroadcast();
+        }
+    }   // ABR WLK end

-- E: MEZI FUNKCE World::ProcessCliCommands() A World::InitResultQueue() VLOŽ NÁSLEDUJÍCÍ FUNKCI:

void World::SendBroadcast() // ABR WLK fce
{
   std::string msg;
   static int nextid;

   QueryResult *result;
   if(nextid == 0)
   {
       result = loginDatabase.PQuery("SELECT `next` FROM `autobroadcast` WHERE `id` = 0"); // ABR WLK - Load after restart
       if (!result) nextid = 1;
       else
       {
           Field *fields = result->Fetch();
           nextid = fields[0].GetUInt32();
           if(nextid == 0) nextid = 1;
           delete result;
       }
   }

   result = loginDatabase.PQuery("SELECT `text`, `next` FROM `autobroadcast` WHERE `id` = %u", nextid);

   if(!result)
       return;

   Field *fields = result->Fetch();
   nextid  = fields[1].GetUInt32();
   msg = fields[0].GetString();
   delete result;

   sWorld.SendWorldText(LANG_AUTO_BROADCAST, msg.c_str());
   sLog.outString("AutoBroadcast: '%s'",msg.c_str());
   loginDatabase.PExecute("REPLACE INTO `autobroadcast`(`id`,`text`,`next`) VALUES (0,'last nextid',%u)", nextid); // ABR WLK - Save next
}   // ABR WLK fce end

 

 

4. CORE side - SOUBOR src/game/World.h

-- A: NAJDI ŘÁDEK WUPDATE_COUNT

-    WUPDATE_COUNT         = 8
+    WUPDATE_AUTOBROADCAST = 8,  // ABR WLK
+    WUPDATE_COUNT         = 9   // ABR WLK

-- B: NAJDI ŘÁDEK void AddSession(WorldSession *s);

+        void SendBroadcast();   // ABR WLK

 

5. CONFIG side - KONFIGURAČNÍ SOUBOR mangosd.conf NAJDI ŘÁDEK Event.Announce =

+AutoBroadcast.On = 1
+AutoBroadcast.Timer = 20

Vysvětlení konfigurace:

AutoBroadcast.On      // 1 = zapnuto, 0 = vypnuto
AutoBroadcast.Timer   // Časová prodleva mezi jednotlivými broadcasty v minutách (výchozí hodnota: 20).

 

Když neumíte patchnout core, nepište sem! Najděte si návod zde na fóru, nebo použijte google.

(Vyjímkou je, pokud vám to opravdu nejde a zdá se vám, že je chyba ve mě.)

Žádám diskuzi JEN k tématu, zkušennosti, názory a nápady na zlepšení. Děkuji. :ermm:

 

EDIT1: Upravena funkce World::SendBroadcast() pro případ chybějícího záznamu AutoBroadcast ID 0.

EDIT2: Trochu jsem to překopal, upravil ukládání, u static int nedefinuju hodnoty (zbytečnost). Thx->bLuma.. :)

Edited by Wolf Officious
  • Upvote 1

Share this post


Link to post
Share on other sites

Osobně bych to načetl jednou z db a pak vypisoval z cache bez nutnosti zásahů do db, ale to je jen detail. Píšu, protože kód generuje memleaky. Při nextid == 0 neuvolňuješ lastnextid a potom pokaždé, když provádíš replace into voláš PQuery, kam ale patří PExecute (tady by k tomu nejspíše dojít nemělo, ale z výkonnostního hlediska je vhodnější použít execute)

Share this post


Link to post
Share on other sites

Šlo by to rozjed na TC2?

 

Na TC už je automaticky zabudovanej AutoBroadcast.

Share this post


Link to post
Share on other sites

Osobně bych to načetl jednou z db a pak vypisoval z cache bez nutnosti zásahů do db, ale to je jen detail. Píšu, protože kód generuje memleaky. Při nextid == 0 neuvolňuješ lastnextid a potom pokaždé, když provádíš replace into voláš PQuery, kam ale patří PExecute (tady by k tomu nejspíše dojít nemělo, ale z výkonnostního hlediska je vhodnější použít execute)

 

Počkej počkej.. Teď si mě trochu rozhodil.. :D Vezmu to od konce.. PExecute, jasně. PQuery je spíš pro select (na dotaz i odpovídá).

 

Teď vidím že jsem tam podělal několik věcí, třeba.. ..ono to fakt.. sakra.. předělám to. :wacko:

 

EDIT: Hele, ty bys vážně chtěl veškerý data z tabulky `autobroadcast` načítat do paměti (podobně jako třeba gameobjecty)? :o

Edited by Wolf Officious

Share this post


Link to post
Share on other sites
EDIT: Hele, ty bys vážně chtěl veškerý data z tabulky `autobroadcast` načítat do paměti (podobně jako třeba gameobjecty)? :o

 

Velikost textu v paměti je mnohem příjemnější než dva dotazy do databáze (sice by pak nebyla funkce, že po restartu začne tam kde skončil) a s ohledem na stávající strukturu a zvyklosti v kódu by to bylo celkem dobře realizovatelné.

A jinak ještě k tvému patchi tak u "static uint32 abtimer = 0;" a "static uint32 autobroadcaston = 0;" je vlastnost static definována k ničemu.

Share this post


Link to post
Share on other sites

Velikost textu v paměti je mnohem příjemnější než dva dotazy do databáze (sice by pak nebyla funkce, že po restartu začne tam kde skončil) a s ohledem na stávající strukturu a zvyklosti v kódu by to bylo celkem dobře realizovatelné.

A jinak ještě k tvému patchi tak u "static uint32 abtimer = 0;" a "static uint32 autobroadcaston = 0;" je vlastnost static definována k ničemu.

 

Jo, to je fakt. Jenže jak to do tý paměti nacpu? Narvu to do struktury?

 

Hele, k tý funkci World::SendBroadcast(), tam jak to čte to last ID, když jsem u "static int nextid = 0;" smazal " = 0", tak se to fakt provádí jenom jednou (myslim ten load last..). Hele, a stejně by se to muselo nějak ošetřit. Já potřebuju ukládat last id po každym broadcastu. Vím, je to blbost, ale štve mě jich tam mít 40 a po každý to začíná od začátku. Původně tam byl na začátku random. Možná bych ho tam vrátil, ale.. já nevím no.

 

První post jsem upravil, koukni na to. Mělo by to už bejt ok.

 

Ale stále nevím jak loadnout ty broadcasty do mem.

Edited by Wolf Officious

Share this post


Link to post
Share on other sites

No ano, uložíš ty hodnoty do nějaké datové struktury k tomu určené (vector, pokud bys vyložene potřeboval explicitní id (vector ti na sekvenční procházení stačí) tak je k dispozici map, unordered_map).

 

Jinak "delete result && fields" je kravina, jenom "delete result".

Share this post


Link to post
Share on other sites

No ano, uložíš ty hodnoty do nějaké datové struktury k tomu určené (vector, pokud bys vyložene potřeboval explicitní id (vector ti na sekvenční procházení stačí) tak je k dispozici map, unordered_map).

 

Jinak "delete result && fields" je kravina, jenom "delete result".

 

"delete result && fields;".. no já myslel že potřebuju smazat i to pole.. :o

 

Sakra, struktury mi nikdy moc nešly. Já to někde v tom core snad najdu a opíšu to.. :D

Share this post


Link to post
Share on other sites

bLumo, tak jsem to hodil do dvou soborů extra, hlavička a cpp..

 

AutoBroadcastMgr.cpp:

#include "AutoBroadcastMgr.h"
#include "ProgressBar.h"
#include "World.h"


AbrMgr::AbrMgr()
{
}

AbrMgr::~AbrMgr()
{
}

AbrMgr& AbrMgr::Instance()
{
   static AbrMgr abrMgr;
   return abrMgr;
}
void AbrMgr::LoadAbrData()
{
   uint32 count = 0;

QueryResult *result = loginDatabase.Query("SELECT id, text, next FROM autobroadcast");
   if (!result)
   {

       barGoLink bar( 1 );

       bar.step();

       sLog.outString();
       sLog.outString( ">> Loaded %u auto broadcast messages", count );
       return;
   }

   barGoLink bar((int)result->GetRowCount());

   do
   {
       Field *fields = result->Fetch();

       bar.step();

       uint32 Abr_ID = fields[0].GetUInt32();

       AutoBroadcastData abd;

       abd.msg    = fields[1].GetString();
       abd.nextid = fields[2].GetUInt32();

	mAutoBroadcastData[Abr_ID] = abd;
       ++count;

   } while( result->NextRow() );

   delete result;

   sLog.outString();
   sLog.outString( ">> Loaded %u auto broadcast messages", count );
}

 

AutoBroadcastMgr.h:

#ifndef _ABRMGR_H
#define _ABRMGR_H

struct AutoBroadcastData
{
   std::string msg;
   uint32 nextid;
};

typedef UNORDERED_MAP<uint32, AutoBroadcastData> AutoBroadcastDataMap;

class AbrMgr
{
   friend struct AutoBroadcastData;

   // Constructors
   public:
       AbrMgr();
       ~AbrMgr();

       static AbrMgr& Instance();
       void LoadAbrData();

   private:
	AutoBroadcastDataMap mAutoBroadcastData;
};
#define sAbrMgr AbrMgr::Instance()
#endif

 

Výsledek: (trapné)

229_mangos_abr_load.png

 

 

No, a teď ještě zbývá to nějak dostat ven. :D (pokud to tam zůstalo) :D (Vím že jsem udělal jenom pitomej loader a musím s těmi daty nějak dál pracovat, ale zatím nemám žádný nápad..)

 

EDIT1: Upraveno.. ..ale stejně na nic.. :D

Edited by Wolf Officious

Share this post


Link to post
Share on other sites

Neměl jsem na mysli tvořit kvůli tomu vlastní třídu, stačilo využít ObjectMgr. Když už, ale vytváříš vlastní singleton třídu tak využij toho čím mangos disponuje (src/framework/Policies/singleton*). Tj v hlavičkovém soubor si zadefinuj makro: #define sAbrMgr MaNGOS::Singleton<AbrMgr>::Instance() a v cpp soubor zavolej "INSTANTIATE_SINGLETON_1(AbrMgr);" (vyžaduje hlavičkový soubor SingletonImp.h).

Stále nechápu k čemu ti je nextid, uvažuješ snad o nějakém inteligentním vybírání těch zpráv ? Pokud se jedná jen o sekvenční seznam použij normální vector. Potom ti stačí udělat si tam veřejnou metodu dejDalsi(), která ti vrátí následující zprávu (stačí si uvnitř třídy uchovat iterátor přes ten vector, když dojde na konec tak ho akorát vyresetuješ na začátek nebo rovnou metodu vypisDalsi(), co vezme zprávu a odešle ji. Vlastní otravování hráčů stejně musíš realizovat přes timer ve World::Update.

Definovat přátelskou strukturu v tom tvém kódu je zbytečné.

Share this post


Link to post
Share on other sites

Dobře, budu se snažit to dát do ObjectMgr. Nebo jestli mi pomůžeš to nějak vychytat tak, jak jsem to začal psát? Já se to pak snažím dostat ven z tý struktury až ve World.cpp, protože tam odkazuje ten timer. Viz. řádek "SendBroadcast();":

    static uint32 autobroadcaston;  // ABR WLK begin
   autobroadcaston = sConfig.GetIntDefault("AutoBroadcast.On", 1);
   if(autobroadcaston == 1)
   {
       if (m_timers[WUPDATE_AUTOBROADCAST].Passed())
       {
           m_timers[WUPDATE_AUTOBROADCAST].Reset();
           SendBroadcast();
       }
   }   // ABR WLK end

 

Do toho AutoBroadcastMgr teď píšu další funkci na výpis, že by to i ten timer po tom odkazoval na to. Mám v tom už solidní zmatek. Opisoval jsem to z funkce LoadSpellTargetPositions() která je v souboru SpellMgr.cpp.

 

Moc nerozumím tomu, co si psal o tom #define, ani nevím co to je Singleton. :ermm:

 

Pomóc! :)

Share this post


Link to post
Share on other sites

Těžko ti něco radit, když ve své třídě použiješ návrhový vzor Singleton a nevíš co to je a že mangos na to má svoji šablonu.

Když už to chceš dělat přes vlastní třídu s minimem zásahů do původního kódu tak tu tvoji třídu měj zhruba takto:

typedef std::string broadcastMessage;
typedef std::vector<broadcastMessage> broadcastMessages

class AbrMgr {
public:
 void LoadFromDB(); // načte z databáze zprávy do vectoru
 void SendNext(); // odešle další zprávu

private:
 broadcastMessages m_mess; // zprávy
 broadcastMessages::iterator m_actualIt; // iterátor pro udržení poslední odeslané zprávy 
};

#define sAbrMgr MaNGOS::Singleton<AbrMgr>::Instance()

Implementace metody SendNext bude něco jako:

if (m_mess.empty())
 return;

m_actualIt++;

if (m_actualIt == m_mess.end())
 m_actualIt = m_mess.begin();

std::string zprava = *m_actualIt;
// odeslání zprávy

Po načtení z db je nutné inicializovat ten iterátor m_acutalIt = m_mess.begin(); Zahazuji zde veškeré informace o id a nextid. V db si zachovej jen ID a podle toho si při načítání seřaď výsledky (order by id)

Ve World::Update ti pak bude stačit něco jako:

    uint32 autobroadcaston = Config.GetIntDefault("AutoBroadcast.On", 1);  // ABR WLK begin
   if(autobroadcaston)
   {
       if (m_timers[WUPDATE_AUTOBROADCAST].Passed())
       {
           m_timers[WUPDATE_AUTOBROADCAST].Reset();
           sAbrMgr.SendNext(); // vyžaduje hlavičkový soubor AbrMgr.h
       }
   }   // ABR WLK end

Psal jsem to z hlavy a některé názvy metod u vector atd. jsem možná netrefil, hlavy si vše fakt nepamatuji.

  • Upvote 2

Share this post


Link to post
Share on other sites

Hele, tak jsem to nakonec udělal nějak sám.

 

AutoBroadcastMgr.h:

#ifndef _ABRMGR_H
#define _ABRMGR_H

#include "Utilities/UnorderedMap.h"

struct AutoBroadcastData
{
   std::string msg;
   uint32 nextid;
};
typedef UNORDERED_MAP<uint32, AutoBroadcastData> AutoBroadcastDataMap;

class AbrMgr
{
   friend struct AutoBroadcastData;

   // Constructors
   public:
       AbrMgr();
       ~AbrMgr();

   // Accessors (const or static functions)
public:
       // AutoBroadcast get data
       AutoBroadcastData const* GetAutoBroadcastData(uint32 abr_id) const
       {
           AutoBroadcastDataMap::const_iterator itr = mAutoBroadcastData.find( abr_id );
           if( itr != mAutoBroadcastData.end( ) )
               return &itr->second;
           return NULL;
       }

       static AbrMgr& Instance();
       void LoadAbrData();

   private:
	AutoBroadcastDataMap mAutoBroadcastData;
};
#define sAbrMgr AbrMgr::Instance()
#endif

 

AutoBroadcastMgr.cpp:

#include "AutoBroadcastMgr.h"
#include "ProgressBar.h"
#include "World.h"


AbrMgr::AbrMgr()
{
}

AbrMgr::~AbrMgr()
{
}

AbrMgr& AbrMgr::Instance()
{
   static AbrMgr abrMgr;
   return abrMgr;
}
void AbrMgr::LoadAbrData()
{
   uint32 count = 0;
   //                                                0   1     2
   QueryResult *result = loginDatabase.Query("SELECT id, text, next FROM autobroadcast");
   if (!result)
   {
       barGoLink bar( 1 );
       bar.step();
       sLog.outString();
       sLog.outString( ">> Loaded %u auto broadcast messages", count );
       return;
   }
   barGoLink bar((int)result->GetRowCount());
   do
   {
       Field *fields = result->Fetch();
       bar.step();
       uint32 Abr_ID = fields[0].GetUInt32();
       AutoBroadcastData abd;
       abd.msg    = fields[1].GetString();
       abd.nextid = fields[2].GetUInt32();
       mAutoBroadcastData[Abr_ID] = abd;
       ++count;
   } while( result->NextRow() );
   delete result;
   sLog.outString();
   sLog.outString( ">> Loaded %u auto broadcast messages", count );
   return;
}

 

World.cpp:

#include "BattleGroundMgr.h"
#include "Language.h" // ABR WLK
+#include "AutoBroadcastMgr.h"  // ABR WLK
#include "TemporarySummon.h"

    sLog.outString( "Loading CreatureEventAI Scripts...");
   sEventAIMgr.LoadCreatureEventAI_Scripts();

+    sLog.outString( "Loading AutoBroadcast Messages..."); // ABR WLK
+    sAbrMgr.LoadAbrData();

   sLog.outString( "Initializing Scripts..." );
   if(!LoadScriptingModule())
       exit(1);

a takhle by mohla nějak vypadat ta funkce send broadcastu (pořát soubor World.cpp):

void World::SendBroadcast() // ABR WLK fce
{
   std::string msg;
   static int nextid;

   if(nextid == 0)
{
	nextid = sAbrMgr.GetAutoBroadcastData(nextid)->nextid;
	sLog.outString("AutoBroadcast last_nextid loaded.");
}

   msg = sAbrMgr.GetAutoBroadcastData(nextid)->msg;

   sWorld.SendWorldText(LANG_AUTO_BROADCAST, msg.c_str());
   sLog.outString("AutoBroadcast ID %u: '%s'",nextid,msg.c_str());

   nextid = sAbrMgr.GetAutoBroadcastData(nextid)->nextid;
   loginDatabase.PExecute("REPLACE INTO `autobroadcast`(`id`,`text`,`next`) VALUES (0,'last_nextid',%u)", nextid);
}   // ABR WLK fce end

 

To, co jsem tady nenapsal, to zůstalo stejný. jenom to budu muset trochu dopsat. Tohle funguje, zprávy se čtou v pořadí z tý struktury tak jak mají (údaj nextid tedy plní svojí funkci dokonale).. last next se čte jenom při první zprávě.

 

VÝSLEDEK:

807_mangos_abr2.png

Edited by Wolf Officious
  • Upvote 1

Share this post


Link to post
Share on other sites

Heleďte se, ještě jsem to předělal, ale teď už většinu. Chci se zeptat moderátorů, jestli můžu založit novej topic, kde bude verze AutoBroadcastu která se načítá do paměti. Jinak bych to napsal sem, upravil bych první post, nebo přidal další (což nebude přehledný). Hodím sem pak link. Ok?

 

bLuma nebo někdo by to tu třeba mohl pročistit podle uvážení. To druhý téma napíšu odpoledne, jo? Zatím prosím nedávejte do core to, co je výš popsané, protože jsem to napsal ještě trochu jinak, líp. Spoustu věcí bylo už v původním "ABR patch" (v prvním postu) zbytečně.

 

Přidávání dvou souborů pro load ABR z DB zůstalo.

 

Takže odpoledne se dočkáte. Nejsem sobec, nenechám si to pro sebe. :)

Share this post


Link to post
Share on other sites

Pokud to bude dlouhý tak klidně založ téma. Ohledně pročištění, napiš sem které příspěvky chceš nechat/smazat (vpravo nahoře je vždy číslo příspěvku tak ty vypiš)

Share this post


Link to post
Share on other sites

Pokud to bude dlouhý tak klidně založ téma. Ohledně pročištění, napiš sem které příspěvky chceš nechat/smazat (vpravo nahoře je vždy číslo příspěvku tak ty vypiš)

No, bude to dlouhý z hruba jako ten první post. Takže asi bych měl založit nový téma (podle mého názoru, navíc to bude přehlednější.).. A jelikož tahle diskuze měla za následek to, že jsem to přepsal do lepší podoby, mělo by tu zůstat tak, jak to tu je teď. Takže napíšu nové téma, tady zůstane rozdělaný kód a v novém bude nový, svěží a sto-procentně Wlčí AutoBroadcast systém. :):D

 

bLuma: Díky, za nápad to dát do mem. Nechtělo se mi to dělat protože jsem o tom moc nevěděl, ale naučil jsem se tím plno nových věcí. Ještě jednou ti děkuju. :) Wlk

Edited by Wolf Officious

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this  

×