EQEmulator Forums

EQEmulator Forums (https://www.eqemulator.org/forums/index.php)
-   Quests::Q&A (https://www.eqemulator.org/forums/forumdisplay.php?f=599)
-   -   Same Item Turn for Changing Quest Globals - Need Help (https://www.eqemulator.org/forums/showthread.php?t=24781)

trevius 04-01-2008 08:26 PM

Same Item Turn for Changing Quest Globals - Need Help
 
So, I am trying to make a quest that will level characters by 1 level each time they turn in 4 ItemID 2835. I can't get it to work properly. I have 2 examples below which I have tried adjustments to, but neither seem to work properly.

First, I tried this script, which uses elsifs, but I haven't really used them much before so it is very possible there could be a mistake. This one does absolutely nothing if I turn in the items. In fact, it doesn't even return them.

Code:

sub EVENT_ITEM {

if (plugin::check_handin(\%itemcount, 2835=>4) {
 
if ($max_level == undef) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 71, 5, "F");
    quest::level(71); }
 
elsif ($max_level == 71) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 72, 5, "F");
    quest::level(72); }
 
elsif ($max_level == 72) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 73, 5, "F");
    quest::level(73); }
 
elsif ($max_level == 73) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 74, 5, "F");
    quest::level(74); }
 
elsif ($max_level == 74) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 75, 5, "F");
    quest::level(75); }

  }

  else {
    plugin::return_items(\%itemcount);
      }

}

The script below is the code that I tried next and it actually works for the first turn in. It gives me the global of 71, the level and everything. But, if I turn in 4 more ItemID 2835s, it just eats them and does nothing. I verified it is putting the global on my character and that the NPC is recognizing globals. I made a simple EVENT_SAY to make sure it responded properly to hails when I had the global max_level at 71 and it responded properly. The npc is flagged for qglobals in the NPC_Entries table. I am stumped as to why it isn't working past the first turn in. My guess is it is something to do with it being the same item that is turned in, which is why I first tried the elseifs in the code above.

Code:

sub EVENT_ITEM {

if (plugin::check_handin(\%itemcount, 2835=>4) && $max_level == undef) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 71, 5, "F");
    quest::level(71); }
 
if (plugin::check_handin(\%itemcount, 2835=>4) && $max_level == 71) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 72, 5, "F");
    quest::level(72); }
 
if (plugin::check_handin(\%itemcount, 2835=>4) && $max_level == 72) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 73, 5, "F");
    quest::level(73); }
 
if (plugin::check_handin(\%itemcount, 2835=>4) && $max_level == 73) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 74, 5, "F");
    quest::level(74); }
 
if (plugin::check_handin(\%itemcount, 2835=>4) && $max_level == 74) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 75, 5, "F");
    quest::level(75); }

  else {
    plugin::return_items(\%itemcount);
      }

}

Any help would be greatly appreciated!

ChaosSlayer 04-01-2008 09:00 PM

hmm could you try this - use the FIRST code sample, but replace "elseif"s with regular "if"s

if it works the way i understand it, it should produce chain leveling reaction =)

trevius 04-01-2008 09:29 PM

Actually, I tried that first and it had the same effect as the elsif's, which was no effect.

Aramid 04-01-2008 09:54 PM

Try adding $max_level=undef; in the script at the end.

ChaosSlayer 04-01-2008 10:52 PM

Quote:

Originally Posted by Aramid (Post 145771)
Try adding $max_level=undef; in the script at the end.

won't this reset the variable every time script runs?

mattmeck 04-01-2008 11:11 PM

Why even use the globals in this case seems to be overkill?


a simple if level 70 and you turn in the item the npc does a #level 71
if level 71 and you turn in the items the npc does #level 72
etc etc

dont feel like writing it up but you get the idea.

ChaosSlayer 04-01-2008 11:31 PM

Quote:

Originally Posted by mattmeck (Post 145774)
Why even use the globals in this case seems to be overkill?


a simple if level 70 and you turn in the item the npc does a #level 71
if level 71 and you turn in the items the npc does #level 72
etc etc

dont feel like writing it up but you get the idea.

yeah I was thinking the same thing, but still it is educational to know why the code won't work anyway.

btw I consulted the popular "credit card" code, and it indeed uses things such as $max_level=undef; after each adjustment statement.

I do not uderstand the processing logic behind it, but apperently this is how it supose to work

trevius 04-02-2008 12:02 AM

Actually, in my real quest scripts, I do have:

Code:

{
$max_level=undef;
}

I only cut out the main part I was working on. I added in the sub EVENT_ITEM part before posting it.

The reason I want globals for this is mainly for my de-level quests. My server has quests to de-level characters to any level they want. Since my server's max level is 70, the quested levels have to be remembered so people can return to their previous level if it is higher than level 70. If I don't use globals on this quest, I will just have to use them on both different types of de-level quests (one is permanent and one is temporary). I figured I might as well define them here if possible.

Also, in reply to Mattmeck; I have a feeling that if qglobals doesn't work when turning in 1 item and having multiple different requirements for the same hand in, I am willing to bet that checking for character level would have the same problem. I will test it tonight. But, I think the issue is with the item check, and it won't let it be checked again for the other IFs. Actually, maybe it is the plugin. Maybe I can try it without it, but those plugins are handy.

Aramid 04-02-2008 02:40 AM

2 Things that will make it work using the If statements.

1st, use different items for each handin. Using the SAME item each time for each level seems to confuse the program. If there is a way to clear the items after handing them in and setting the new setglobal, before the next if statememt, then it may work.

To make it properly return the items if they are not correct, add a return;.

Code:

else
 {
    plugin::return_items(\%itemcount);
    return;
 }


Aramid 04-02-2008 03:06 AM

I'm SLOW but persistant... LOL

The following is working perfectly on my system.... As you can see, you only can have 1 if for the items and then do your multiple checks for the max_level. Even returns multiple incorrect items.

Code:

sub EVENT_ITEM {

if (plugin::check_handin(\%itemcount, 2835 => 4)){
  if ($max_level ==undef) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
    $client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 71, 0, "F");
    quest::level(71);
  }
  elsif ($max_level == 71) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
  $client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 72, 0, "F");
    quest::level(72);
  }
  elsif ($max_level == 72) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
    $client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 73, 0, "F");
    quest::level(73);
  }
  elsif ($max_level == 73) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 74, 0, "F");
    quest::level(74);
  }
  elsif ($max_level == 74) {
    quest::say("These are in excellent shape!  They will be trophies in my collection!");
$client->Message(6, "Maximus Serilious rewards you with a new level!" );
    quest::exp(9999999);
    quest::setglobal("max_level", 75, 0, "F");
    quest::level(75);
  }
 }
    else
  {
    quest::emote("I have no use for this item");
    plugin::return_items(\%itemcount);
    return;
  }
}

I'm too tired to do it now, but you will want to have a check for the last max_level to give back the items when they are AT the max_level of 75!

AndMetal 04-02-2008 03:18 AM

Quote:

Originally Posted by Aramid (Post 145785)
Using the SAME item each time for each level seems to confuse the program.

That's because plugin::check_handin removes the items from the %itemcount array. I believe this is why it only gets through the first check in the second set of code in the first post.

Then again, there looks to be a syntax error in the 1st set of code, which should do what you're trying to do:
Code:

if (plugin::check_handin(\%itemcount, 2835=>4) {
should be
Code:

if (plugin::check_handin(\%itemcount, 2835=>4)) {
Quote:

Originally Posted by Aramid (Post 145785)
If there is a way to clear the items after handing them in and setting the new setglobal, before the next if statememt, then it may work.

I think this would do the trick:

Code:

sub EVENT_ITEM {
        if ($itemcount{2835} == 4 && $qglobals{max_level} == undef) {
                quest::say("These are in excellent shape!  They will be trophies in my collection!");
                $client->Message(6, "Maximus Serilious rewards you with a new level!" );
                quest::exp(9999999);
                quest::setglobal("max_level", 71, 5, "F");
                quest::level(71);
                $itemcount{2835} = undef;
        }
        if ($itemcount{2835} == 4 && $qglobals{max_level} == 71) {
                quest::say("These are in excellent shape!  They will be trophies in my collection!");
                $client->Message(6, "Maximus Serilious rewards you with a new level!" );
                quest::exp(9999999);
                quest::setglobal("max_level", 72, 5, "F");
                quest::level(72);
                $itemcount{2835} = undef;
        }
        Etc...
        Etc...
        Etc...
}

Something else you could do to really trim the code down:

Code:

sub EVENT_ITEM {
        if (plugin::check_handin(\%itemcount, 2835 => 4)) {
                quest::say("These are in excellent shape!  They will be trophies in my collection!");
                quest::exp(9999999);
                if ($qglobals{max_level} == undef) {
                        quest::setglobal("max_level", 71, 0, "F");
                        quest::level(71);
                } elsif ($qglobals{max_level} >= 75) {
                        plugin::return_items(%itemcount);
                } else {
                        quest::setglobal("max_level", $qglobals{max_level}++, 0, "F"
                        quest::level($qglobals{max_level})
                }
        } else {plugin::return_items(%itemcount);}
}


trevius 04-02-2008 06:07 AM

Thanks guys! I really appreciate the help! Turned out after all of that it was just that little typo that I missed a right parenthesis that AndMetal pointed out.

It is working now. The only problem I am still having is with it returning items after the player is at global 75. That isn't really a problem, since they won't have a use after that point anymore anyway. And I am pretty sure I can get it figured out on my own.

Bulle 04-02-2008 01:25 PM

The "handin" plug-in is a facility to check that a player gives the proper items, and consume them if it is the case. It should really be used as the last check in an "if" chain, as it performs a side-effect (removes the given items, they are given it is too late).

So you can probably avoid having the player "loose" the items by first checking for your max_level (and anything else), then when all conditions are fulfilled perform the hand-in. Basically you check that the PC fulfills the conditions for the hand-in, then you have the NPC accept the items. "accept-and-eat" would be a good description for the "handin".

Another solution you have is to re-summon the given items in case you use "handin" first (gulp the items are eaten, only use with troll NPCs:D). Add a summonitem instruction with the item ID and 4 occurences. The "return_items" plugin does just that.

Or if you want to make tests on the items given by the player before doing other tests (may be in some case you would like to), you can always return to the definition of the "handin" and use the "$itemcount" map, which associates given item IDs to the amount of items given. Remeber to check that an item has been given before checking its amount. You can even adjust the amount given as you want, in the same way "handin" works.
For example you could use (from a silly quest I have been writing) :
Code:

if(defined($itemcount{13078}) && $itemcount{13078} >= 4 # Summoned: Black Bread)
    {
      $itemcount{13078} = $itemcount{13078} - 4; # Summoned: Black Bread
      if($itemcount{13078} == 0)
      { delete $itemcount{13078}; }
      quest::say("Groumph ! It fuud, but not guud. Belux said me eat dat ? OK me eat. Me not want Glob froglok.");

I hope this clears out how "handin" works. In fact it is a quite small function, worth reading for sure.

ChaosSlayer 04-02-2008 01:39 PM

I have a related question - how would you write a code for NPC to automaticly return anything given wihout checkign for specific item?

So far I only figured out how to do it by checking for item which does not even exist (id 1000), but there got to be way to do it simpler?

Code:

sub EVENT_ITEM
{
        if (plugin::check_handin(\%itemcount,1000=>1))
        {
        quest::say("imposible just happened");       
        }

        else
        {
        plugin::return_items(\%itemcount);       
        }
}


Bulle 04-02-2008 01:51 PM

I do not know how other people do, but I use my little spoon.

OK silly reference to a joke about consultants, may be only known in France sorry :)

More to the point I simply do :
sub EVENT_ITEM
{
plugin::return_items(\%itemcount);
}

and it works. I saw in another thread it could be done as a default for all NPCs without quests (and may be it is in PEQ right now).


All times are GMT -4. The time now is 10:58 AM.

Powered by vBulletin®, Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.