Go Back   EQEmulator Home > EQEmulator Forums > Support > Support::Windows Servers

Support::Windows Servers Support forum for Windows EQEMu users.

Reply
 
Thread Tools Display Modes
  #1  
Old 06-04-2011, 02:12 PM
Zothen
Hill Giant
 
Join Date: Apr 2011
Location: Germany
Posts: 163
Question Loottables

1.

Lets take Gynok Moltor for example:

He got 2 lootdrops : 2885 and 90097, but...

2885 has a probability of 50 and
90997 a probability of 100.

Is this supposed to work? Is the probability added up to 150 and then divided? Or is the lootdrop 90997 always rolled and 2885 does not have any chance to drop?


2. Can I make a lootdrop with a probability of 1/1000 for example?

3.
Another question:
I saw loottables with only 1 lootdrop in it, which sometimes got a probability below 100. Well, thats okay as some mobs arent supposed to drop loot every time. But what about the "chance" column in the lootdrop_entries table? Do the chances sum need to be 100?
Reply With Quote
  #2  
Old 06-04-2011, 03:26 PM
Wolfling
Fire Beetle
 
Join Date: Sep 2010
Posts: 21
Default

1. 2885
50 means its a 50% chance it will be picked, if it does, then it looks in the loot entries which on mine has a 5or6% chance to drop one of the rusty weapons,

90097 is 100, so will always get selected, and one of the two rings will get selected, as they are set 50/50 - so you will always get one of them
if you changes the multiplier to 2, then you always get 2 rings

2. you could, just give it low odds, 5% probability of being picked 5% chance of dropping the item ( that isn't the math, play around with it )

3. as explained above, and no, chance dosn't have to =100 that is why sometimes you will get nothing from that loot entry
Reply With Quote
  #3  
Old 06-06-2011, 05:22 AM
Zothen
Hill Giant
 
Join Date: Apr 2011
Location: Germany
Posts: 163
Default

Thank you very much!
Reply With Quote
  #4  
Old 06-06-2011, 06:21 AM
trevius's Avatar
trevius
Developer
 
Join Date: Aug 2006
Location: USA
Posts: 5,946
Default

Maybe I am misunderstanding the explanation above, but this is how it works:

The chance field of the lootdrop_entries table does not have to equal 100. No matter what the total is for all entries in that lootdrop_id, the chance is basically a percentage of the total of the entries.

Here are some examples:

1. If there is only 1 lootdrop entry, the chance is 100% no matter if you set it to 1 or to 100.

2. If there are 3 loot drop entries that you want to all have equal drop chances, you can set each to 33, or you can set each to 100 or any other equal value and the chance will be divided equally.

3. If you have 3 entries and 1 is 100 and the other 2 are 50, then 1 of them will have 50% chance while the other 2 have 25% chance each.

Basically, it just totals up the chances and randoms and sees if the random outcome is less than the chance of the entry it is checking.
__________________
Trevazar/Trevius Owner of: Storm Haven
Everquest Emulator FAQ (Frequently Asked Questions) - Read It!
Reply With Quote
  #5  
Old 06-06-2011, 10:34 AM
Zothen
Hill Giant
 
Join Date: Apr 2011
Location: Germany
Posts: 163
Default

And the chance column works the same way as the probability column?

If thats really the way it works, then do I really always get 2 items of one lootdrop when the multiplier is set to 2? Wouldnt it be more random if I can get 0-2 items of a lootdrop, setting the multplier to 2 and the lootdrop entries to a max total chance of 50? Or is THAT handled with probability?
Reply With Quote
  #6  
Old 06-06-2011, 10:46 AM
image
Demi-God
 
Join Date: Jan 2002
Posts: 1,290
Default

for (int32 i=0; i<lts->NumEntries; i++) {
for (int32 k = 1; k <= lts->Entries[i].multiplier; k++) {
if ( MakeRandomInt(0,99) < lts->Entries[i].probability) {
AddLootDropToNPC(npc,lts->Entries[i].lootdrop_id, itemlist);
}
}

pretty much:
- For each lootdrop entry that exists on the mob we iterate (tied to whatever x loottable).
- Then inside each lootdrop, we iterate x times (multiplier).
- Inside the nested for loop we use a random 0-99, if the value is less than the probability you set, we attempt to spawn an item from that lootdrop.

In AddLootDropToNPC (determine the actual item):
- We add up the all the 'chance' values into totalchance (of each item in lootdrop_entries).
- To hit a good chance (its a RandomInt 0-totalchance). The random value must be chance=0 OR chance=100 OR this is the only item in the table (totalchance=itemchance) OR finally the random value is less than the current item chance. The first item that hits one of these conditions is your result. These should order as they are in the DB (so the first lootdrop_entries entry for this lootdrop in the db is the first item entry we check).
__________________
www.eq2emu.com
EQ2Emu Developer
Former EQEMu Developer / GuildWars / Zek Seasons Servers
Member of the "I hate devn00b" club.
Reply With Quote
  #7  
Old 06-06-2011, 11:11 PM
trevius's Avatar
trevius
Developer
 
Join Date: Aug 2006
Location: USA
Posts: 5,946
Default

Yeah, that explanation pretty much covers it all. The only correction I would make is about this:

Quote:
Originally Posted by image View Post
These should order as they are in the DB (so the first lootdrop_entries entry for this lootdrop in the db is the first item entry we check).
To help decrease favoritism for items earlier in the DB order, we instead pick a random point in the total list to start at and then iterate until we get a successful roll. So, if we have 10 items in the same lootdrop_id, we would random 1 to 10 and (or 0 to 9 whatever) and start at the random spot that was picked, then continue to the next and so on.

On the question of multiple drops; that is set in the lootable_entries table with the multiplier and probability fields. So, if you want 0 to 2 possible drops from your lootdrop_id, you can set the multiplier to 2, then the probability to anything from 1 to 99 depending on how often you want 1 or 2 to drop. The multiplier is the max possible items from the lootdrop_id that can be dropped, and the probability is the chance for each multiplier to drop. If you set the multiplier to 10 and the probability to 10%, you would probably average about 1 drop per kill (in theory anyway), but could be anywhere from 0 to 10 at any time.
__________________
Trevazar/Trevius Owner of: Storm Haven
Everquest Emulator FAQ (Frequently Asked Questions) - Read It!

Last edited by trevius; 06-06-2011 at 11:18 PM..
Reply With Quote
  #8  
Old 06-07-2011, 08:10 AM
Zothen
Hill Giant
 
Join Date: Apr 2011
Location: Germany
Posts: 163
Default

I am enlightened now

well, almost...

lootdrop example:
lootdrop1 multiplier 1 prob 50
lootdrop2 multiplier 2 prob 100

so 3 lootdrop rolls altogether, right? lets say first roll is 43, it yields an item from lootdrop1, the other 2 rolls dont matter, cause its a guaranteed drop, makes a total of 3 item drops...?

Now to the chances. Does the current server release really favors items on top of the list or not? I remember reading an older post from you, trevius, about that topic...
Reply With Quote
  #9  
Old 06-07-2011, 08:24 AM
image
Demi-God
 
Join Date: Jan 2002
Posts: 1,290
Default

SELECT lootdrop_id, item_id, item_charges, equip_item, chance FROM lootdrop_entries WHERE lootdrop_id=%i order by chance desc

Thats the actual mysql query to get the lootdrop entries. They are added into memshare this way (so first result from this query is pos 0, second is position 1, etc.). Unless there is something else Trevius is talking about.
__________________
www.eq2emu.com
EQ2Emu Developer
Former EQEMu Developer / GuildWars / Zek Seasons Servers
Member of the "I hate devn00b" club.
Reply With Quote
  #10  
Old 06-07-2011, 08:51 AM
trevius's Avatar
trevius
Developer
 
Join Date: Aug 2006
Location: USA
Posts: 5,946
Default

Here is the code that handles the loot drops being added. Note the part highlighted in green where it picks a random entry from the total number of entries to start at and resets it back to 0 if it rolls past the end of the list.

loottables.cpp
Code:
// Called by AddLootTableToNPC
// maxdrops = size of the array npcd
void ZoneDatabase::AddLootDropToNPC(NPC* npc,int32 lootdrop_id, ItemList* itemlist) {
        const LootDrop_Struct* lds = GetLootDrop(lootdrop_id);
        if (!lds) {
         //   LogFile->write(EQEMuLog::Error, "Database Or Memory error GetLootDrop(%i) == 0, npc:%s", lootdrop_id, npc->GetName());
                return;
        }
        if(lds->NumEntries == 0)        //nothing possible to add
                return;

// This is Wiz's updated Pool Looting functionality.  Eventually, the database format should be moved over to use this
// or implemented to support both methods.  (A unique identifier in lootable_entries indicates to roll for a pool item
// in another table.
#ifdef POOLLOOTING
        printf("POOL!\n");
        int32 chancepool = 0;
        int32 loot_items[100];
        int8  equipitem[100];
        int32 itemchance[100];
        int16 itemcharges[100];
        int8 i = 0;

        for (int m=0;m < 100;m++) {
                loot_items[m]=0;
                itemchance[m]=0;
                itemcharges[m]=0;
                equipitem[m]=0;
        }

        for (int k=0; k<lds->NumEntries; k++)
        {
                loot_items[i] = lds->Entries[k].item_id;
                int chance = lds->Entries[k].chance;
                itemcharges[i] = lds->Entries[k].item_charges;
                equipitem[i] = lds->Entries[k].equip_item;

                /*
                im not sure what this is trying to accomplish...
                LinkedListIterator<ServerLootItem_Struct*> iterator(*itemlist);
                iterator.Reset();
                while(iterator.MoreElements())
                {
                         if (iterator.GetData()->item_id == loot_items[i])
                         {
                                chance /= 5;
                         }
                         iterator.Advance();
                }*/

                chance += chancepool;
                chancepool += lds->Entries[k].chance;
                itemchance[i] = chance;
                i++;
        }
        int32 res;
        i = 0;

    if (chancepool!=0) { //avoid divide by zero if some mobs have 0 for chancepool
        res = MakeRandomInt(0, chancepool-1);
    }
    else {
        res = 0;
    }

        while (loot_items[i] != 0) {
                if (res <= itemchance[i])
                        break;
                else
                        i++;
        }
        const Item_Struct* dbitem = GetItem(items[i]);
        npc->AddLootDrop(dbitem, itemlist, lds->Entries[k].item_charges, lds->Entries[k].equip_item, false);

#else
        //non-pool based looting

        int32 r;
        int32 totalchance = 0;
        for (r = 0; r < lds->NumEntries; r++) {
                totalchance += lds->Entries[r].chance;
        }
        uint32 thischance = 0;
        unsigned short k;
        bool found = false;

        k = MakeRandomInt(0, lds->NumEntries-1);

        while(!found) {

                if (k > (lds->NumEntries - 1)) {
                        k = 0;
                }

                thischance = lds->Entries[k].chance;
                unsigned int drop_chance = MakeRandomInt(0, totalchance-1);
#if EQDEBUG>=11
                        LogFile->write(EQEMuLog::Debug, "Drop chance for npc: %s, total chance:%i this chance:%i, drop roll:%i", npc->GetName(), totalchance, thischance, drop_chance);
#endif
                if (   totalchance == 0
                        || thischance == 100
                        || thischance == totalchance // only droppable item in loot table
                        || drop_chance < thischance     //can never be true if thischance is 0
                        ) {
                        found = true;
                        int32 itemid = lds->Entries[k].item_id;

                        const Item_Struct* dbitem = GetItem(itemid);
                        npc->AddLootDrop(dbitem, itemlist, lds->Entries[k].item_charges, lds->Entries[k].equip_item, false);

                        break;
                        //continue;
                }       //end if it will drop
                k++;    //Cycle to the next droppable item in the list
        }       //end loop
#endif

}
This should prevent it from favoring items at the top of the list. It has been a while since I really looked into how these are all handled (not since that old thread Zothen referred to), but I think the way I described things so far in this thread should be accurate.

And yes, Zothen, your example of having 3 drops from that setup is correct. With those settings, you could have either 2 or 3 drops, depending on if the 50% probability one wins the roll or not.
__________________
Trevazar/Trevius Owner of: Storm Haven
Everquest Emulator FAQ (Frequently Asked Questions) - Read It!

Last edited by trevius; 06-07-2011 at 08:57 AM..
Reply With Quote
  #11  
Old 06-07-2011, 08:54 AM
image
Demi-God
 
Join Date: Jan 2002
Posts: 1,290
Default

Gotcha. nm
__________________
www.eq2emu.com
EQ2Emu Developer
Former EQEMu Developer / GuildWars / Zek Seasons Servers
Member of the "I hate devn00b" club.
Reply With Quote
  #12  
Old 06-09-2011, 02:52 AM
Zothen
Hill Giant
 
Join Date: Apr 2011
Location: Germany
Posts: 163
Default

Thank you both very much! That was very helpful.
Reply With Quote
  #13  
Old 06-14-2011, 12:50 AM
quetark's Avatar
quetark
Fire Beetle
 
Join Date: Jul 2010
Location: Wisconsin
Posts: 25
Unhappy

I'm pretty sure I understand all of this conversation and it's right in line with what I figured out on my own, but I must be missing something because I can't seem to get my new loot to drop. My goal was this: Get all the mobs that are supposed to drop the "ornate defiant scepter" (item ID: 50557) to drop it.

I started by trying to get Hill Giants in Rathe Mts to drop it 100% of the time, just so I could see it drop and then I'd back the % off to about 5. Here's what I did:

1. Add an entry into lootdrop_entries. the previous high value was 90495 so I made mine 90496:
insert into lootdrop_entries (lootdrop_id, item_id, item_charges, equip_item, chance) VALUES (90496, 50557, 1, 0, 100);
[Aside: does 'equip_item' mean the hill giant would have it equipped as his weapon?]

2. figure out that hill giants in rathe mts all use the same loot table (1839):
SELECT npc_types.id,npc_types.name,npc_types.loottable_id
FROM npc_types JOIN spawnentry ON npc_types.id=spawnentry.npcID
JOIN spawn2 ON spawnentry.spawngroupID = spawn2.spawngroupID
JOIN zone ON spawn2.zone = zone.short_name
where npc_types.name='a_hill_giant' and short_name='rathemtn';

3. Add a new entry into that loot table for my new loot drop, giving it a 100% chance of dropping:
insert into loottable_entries (loottable_id, lootdrop_id, multiplier, probability) VALUES (1839, 90496, 1, 100);

That seems pretty straight-forward to me, but none of my hill giants have dropped a scepter. What did I do wrong?
Reply With Quote
  #14  
Old 06-14-2011, 02:11 AM
blackdragonsdg
Dragon
 
Join Date: Dec 2008
Location: Tennessee
Posts: 654
Default

quetark, you appear to be missing the lootdrop entry. Try this:

Code:
INSERT INTO `lootdrop` (`id`, `name`) VALUES (90496, 'HG');
Reply With Quote
  #15  
Old 06-14-2011, 02:31 AM
trevius's Avatar
trevius
Developer
 
Join Date: Aug 2006
Location: USA
Posts: 5,946
Default

Also make sure you restarted your server after you added the loot tables so they can take effect.
__________________
Trevazar/Trevius Owner of: Storm Haven
Everquest Emulator FAQ (Frequently Asked Questions) - Read It!
Reply With Quote
Reply


Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump

   

All times are GMT -4. The time now is 07:59 PM.


 

Everquest is a registered trademark of Daybreak Game Company LLC.
EQEmulator is not associated or affiliated in any way with Daybreak Game Company LLC.
Except where otherwise noted, this site is licensed under a Creative Commons License.
       
Powered by vBulletin®, Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Template by Bluepearl Design and vBulletin Templates - Ver3.3