Author Topic: Random Buried Treasure and Maps  (Read 704 times)

Legacy_JerrodAmolyan

  • Full Member
  • ***
  • Posts: 175
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #15 on: August 08, 2013, 10:04:53 pm »


               *Sigh* Okay, everything works now '<img'> Nothing else is wrong than I won't get any treasure in the chest. Tried to do the source chest thingie, since I cringe at the thought of having to type the resrefs of every item ^^ Oh well... Thanks, this thing works from your part, now I just gotta get it spawn treasure.

(Tried to make it set SourceChest string to a tag of a chest filled with junk, decent or jackpot stuff depending on the dice roll. Not sure why it doesn't work... I guess you can't set and immediately check for a variable '<img'>)
               
               

               
            

Legacy_Squatting Monk

  • Hero Member
  • *****
  • Posts: 776
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #16 on: August 08, 2013, 10:10:13 pm »


               You usually can't set and then get variables off of an object during the same script that creates it. That said, show me your code. I'll see what I can do.
               
               

               


                     Modifié par Squatting Monk, 09 août 2013 - 07:40 .
                     
                  


            

Legacy_JerrodAmolyan

  • Full Member
  • ***
  • Posts: 175
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #17 on: August 08, 2013, 10:15:16 pm »


               *Got it working* Didn't need variables after all. Just made it pick from the source chests directly and duplicate the randomly picked item to the treasure chest.
               
               

               
            

Legacy_JerrodAmolyan

  • Full Member
  • ***
  • Posts: 175
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #18 on: August 08, 2013, 10:16:06 pm »


               // Local variable name for the PC who found the treasure.
const string TREASURE_PC = "TreasurePC";

// Local variable name for a flag noting the treasure has been opened.
const string TREASURE_OPENED = "TreasureOpened";

// Delay to destroy treasure container after it is first opened
// Default: 180 seconds (3 IRL minutes).
const float TREASURE_DELAY = 180.0;

void MakeTreasure(string sChest,object oChest)
{
int nCountItems;
int nRandomItem;
object oSource;
object oItem;
string sResRefItem;
oSource = GetObjectByTag(sChest);
if(!GetIsObjectValid(oSource))return;
//count item logic
oItem=GetFirstItemInInventory(oSource);
nCountItems = 0;
while(GetIsObjectValid(oItem)){
   nCountItems++;
   oItem=GetNextItemInInventory(oSource);
}
//now get random item
nRandomItem=Random(nCountItems)+1;
oItem=GetFirstItemInInventory(oSource);
while(nRandomItem>1){
 nRandomItem--;
 oItem=GetNextItemInInventory(oSource);
}
sResRefItem = GetResRef(oItem);
CreateItemOnObject(sResRefItem,oChest);
}


void main()
{
   // Get the PC opening the treasure and make sure it's the one who found it.
   object oPC = GetLastOpenedBy();
   object oThisChest = OBJECT_SELF;
   string sSourceChest; // Source of Treasure
   sSourceChest = GetLocalString(oThisChest,"SourceChest");
   if (GetLocalObject(OBJECT_SELF, TREASURE_PC) != oPC)
   {
       // It's not the same person, send them a message and abort. This is to
       // prevent someone from sniping treasure from its rightful owner.
       FloatingTextStringOnCreature("This treasure was found by someone else.", oPC, FALSE);
       AssignCommand(oPC, ClearAllActions());
       return;
   }

   // If it's the first time this treasure is being opened, spawn some treasure
   // and then DelayCommand() the treasure's destruction.
   if (!GetLocalInt(OBJECT_SELF, TREASURE_OPENED))
   {
       // Flag the treasure as having been opened before.
       SetLocalInt(OBJECT_SELF, TREASURE_OPENED, TRUE);

       // Delay the destruction of the treasure so it won't tie up this
       // treasure waypoint indefinitely. We do this before creating the
       // treasure in case any custom code added to the treasure generation
       // code times us out.
       DestroyObject(OBJECT_SELF, TREASURE_DELAY);

       // Create treasure on the container. We'll roll a d20 and base the
       // quality of the find on the roll.
       switch (d20())
       {
           // On a roll of 1-5, find junk.
           case 1: case 2: case 3: case 4: case 5:
           {       // Set a local string.

               FloatingTextStringOnCreature("Oi! This is ****!", oPC, FALSE);
               // Creation code here.
                  MakeTreasure("jer_src_****treasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_****treasure",oThisChest);
                   if(d3() > 1 ) MakeTreasure("jer_src_****treasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_****treasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_****treasure",oThisChest);
           } break;

           // On a roll of 6-19, find decent treasure.
           case 6:  case 7:  case 8:  case 9:  case 10:
           case 11: case 12: case 13: case 14: case 15:
           case 16: case 17: case 18: case 19:
           {
               FloatingTextStringOnCreature("Aye! Not bad!", oPC, FALSE);
               // Creation code here.
                  MakeTreasure("jer_src_decenttreasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_decenttreasure",oThisChest);
                   if(d3() > 1 ) MakeTreasure("jer_src_decenttreasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_decenttreasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_decenttreasure",oThisChest);

           } break;

           // On a roll of 20, find ph4t l00t!
           case 20:
           {
               FloatingTextStringOnCreature("Arr! This be a jackpot!", oPC, FALSE);
               // Creation code here.
                   MakeTreasure("jer_src_jackpottreasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_jackpottreasure",oThisChest);
                   if(d3() > 1 ) MakeTreasure("jer_src_jackpottreasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_jackpottreasure",oThisChest);
                   if(d2() > 1 ) MakeTreasure("jer_src_jackpottreasure",oThisChest);
           } break;
       }
   }
}
               
               

               
            

Legacy_JerrodAmolyan

  • Full Member
  • ***
  • Posts: 175
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #19 on: August 08, 2013, 10:19:15 pm »


               That one works now, I just need to fine tune it a bit, I took parts from my random treasure system and merged that with what you gave me.
               
               

               
            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #20 on: August 09, 2013, 12:10:01 am »


               

Squatting Monk wrote...

You usually can't set and then get variables off of an object during the same script that creates it.

Sure you can. Never had an issue with that, and a ton of stuff in our mod wouldn't work without it. Lest ye doubt, here's a test function:


void main()
{
    object oPC = GetLastUsedBy();
    object oItem = CreateItemOnObject("nw_cloth020", oPC);
    int nX, nCheck;
    for (nX = 0; nX < 20; nX++) {
        SetLocalInt(oItem, "Test", nX+1);
        nCheck = GetLocalInt(oItem, "Test");
        SpeakString(IntToString(nCheck) + " = Test var value");
    }
}

Funky
               
               

               
            

Legacy_Squatting Monk

  • Hero Member
  • *****
  • Posts: 776
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #21 on: August 09, 2013, 12:35:40 am »


               Seems I was wrong. Thanks for the correction, Funky. '<img'>
               
               

               
            

Legacy_JerrodAmolyan

  • Full Member
  • ***
  • Posts: 175
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #22 on: August 09, 2013, 11:33:41 am »


               Ok, I have it working mostly like I want it to, Only problem I have now are stackable items (Misc item coins, potions, arrows) that have a stack set as something. I know it can be done so that it will create the stack of item it picks (For example I have different versions of same coin with different stack size) instead of picking 1 item from the stack... What should I add to that script so it will grab the whole stack if the random roll hits that item ?
               
               

               
            

Legacy_meaglyn

  • Hero Member
  • *****
  • Posts: 1451
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #23 on: August 09, 2013, 12:32:04 pm »


               The Lexicon is a good source of info. See the entry for CreateItemOnObject.

Something like this would probably do it:

int nStack  = GetItemStackSize(oItem);
sResRefItem = GetResRef(oItem);
CreateItemOnObject(sResRefItem,oChest, nStack);

Or collapse it a bit:
CreateItemOnObject(sResRefItem,oChest, GetItemStackSize(oItem));
               
               

               
            

Legacy_JerrodAmolyan

  • Full Member
  • ***
  • Posts: 175
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #24 on: August 09, 2013, 01:56:39 pm »


               That looks good otherwise, but I'm using source chests so I don't have to write up all the resrefs, will it work with those too ?
               
               

               
            

Legacy_ruadhri10

  • Jr. Member
  • **
  • Posts: 52
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #25 on: August 09, 2013, 02:33:47 pm »


               As long as you're setting the chest's tag to something unique, you should be able to GetNearestObjectByTag. Otherwise you can use GetNearestObject, but that's more error prone.

FWIW, it IS possible to spawn things in random locations and be confident that they are walkable :-) Its a bit of a hack though, and uses a lot of system resources. The trick is to create a CREATURE in the random location. The engine won't let a creature be created on an unwalkable location, it shunts the creature sideways to a walkable location. So you create the creature, then use GetLocation to save its safe walkable location, destroy the creature, and create your placeable on the saved location. I have used this for random resource placement scripts.

But other posters were correct in telling you to use manually placed scattered waypoints instead - much easier. Hope this helps :-)
               
               

               
            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #26 on: August 09, 2013, 02:41:17 pm »


               

ruadhri10 wrote...

FWIW, it IS possible to spawn things in random locations and be confident that they are walkable :-) Its a bit of a hack though, and uses a lot of system resources. The trick is to create a CREATURE in the random location. The engine won't let a creature be created on an unwalkable location, it shunts the creature sideways to a walkable location. So you create the creature, then use GetLocation to save its safe walkable location, destroy the creature, and create your placeable on the saved location. I have used this for random resource placement scripts.

But other posters were correct in telling you to use manually placed scattered waypoints instead - much easier. Hope this helps :-)


The NWNX function I mentioned is much simpler, but that isn't the stumbling block. Making sure that the pc can REACH the walkable location is.

Funky
               
               

               
            

Legacy_meaglyn

  • Hero Member
  • *****
  • Posts: 1451
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #27 on: August 09, 2013, 03:14:32 pm »


               

JerrodAmolyan wrote...

That looks good otherwise, but I'm using source chests so I don't have to write up all the resrefs, will it work with those too ?


Was this in response to what I posted? If so then, yes.. The lines I posted were modified versions of what you posted in your script.  Change createobject line in the maketreasure routine to include using the stacksize for the item you are using from the chest.

Cheers,
meaglyn
               
               

               
            

Legacy_Squatting Monk

  • Hero Member
  • *****
  • Posts: 776
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #28 on: August 09, 2013, 08:39:02 pm »


               

FunkySwerve wrote...

The NWNX function I mentioned is much simpler, but that isn't the stumbling block. Making sure that the pc can REACH the walkable location is.

He had actually said that didn't matter to him because he was going to be working on climbing, swimming, etc. scripts for those unreachable places. However, having to set all that up just to get the treasure map system working seems like far too much work for so little payoff (especially for a novice scripter).
               
               

               


                     Modifié par Squatting Monk, 09 août 2013 - 07:50 .
                     
                  


            

Legacy_FunkySwerve

  • Hero Member
  • *****
  • Posts: 2325
  • Karma: +0/-0
Random Buried Treasure and Maps
« Reply #29 on: August 09, 2013, 11:19:51 pm »


               

Squatting Monk wrote...

FunkySwerve wrote...

The NWNX function I mentioned is much simpler, but that isn't the stumbling block. Making sure that the pc can REACH the walkable location is.

He had actually said that didn't matter to him because he was going to be working on climbing, swimming, etc. scripts for those unreachable places. However, having to set all that up just to get the treasure map system working seems like far too much work for so little payoff (especially for a novice scripter).


Yes, I read that. It doesn't make it any less a stumbling block. Consider this: for any given walkable area, you must first determine if there is a walkable path to it. That, by itself, is an enormous undertaking, since you must at a minimum track it back to an area transition, while accounting for placeables. I'm honestly not sure how I would go about doing that. Then, if there isn't one, you must then determine if there is some other way of reaching that spot - such as a climbing rope, swimming, etc. That would ALSO be an enormous undertaking, since you would have to retrofit into your system every other system that offered a potential means of ingress to an otherwise unapproachable point - even fitting in one such system, like climbing, would present serious difficulties akin to finding the initial walkable path.

The only way I could think of that is remotely feasible would be to half-ass it, by adopting the assumption that any walkable spot in the mod will either be accessible or ruled out as a treasure spawning spot at some point in the future. You'd wind up hacking in edits for months or years as players stumbled upon new inaccessible treasures. Just not a great way to do things, when much simpler and semi-equivalent approaches are available.

Randomness mostly adds a sense of verisimilitude which is just as easily obtained by planting a sufficient number of pre-placed spots. That's actually the approach we adopted for our secret systems - pre-set spots, only a random selection of which are active on any given reset.

Funky