View Single Post
  #1  
Old 04-04-2009, 02:27 PM
realityincarnate
Developer
 
Join Date: Dec 2007
Posts: 122
Default Merchant Inventory Quest Commands

I don't know of any Live-like functions that would use these commands, so I guess they belong in the custom code section.

This code adds two new perl commands: quest::MerchantSetItem and quest::MerchantCountItem, which are used to access a merchant's temporary inventory list. They can be called from any quest script, not just the merchant in question. I can think of quite a few ways that these could be used, but I have two specific uses on my server. The first is a tradeskills merchant who sells items from zones that aren't accessible yet (garlic, lemons, lemming fur, geodes, etc.) He randomly selects a couple of items to sell, and the selections change each game day.
The second use is a set of caravan quests. By completing the quests for caravan masters in different towns, trade routes are set up and different items and potions appear on the caravan merchants.

Syntax:
quest::MerchantSetItem(merchant's npc id, item id, quanity of item) - changes the number of the item that the merchant has available to sell
quest::MerchantCountItem(merchant npc id, item id) returns the number of that item in stock.

Code:
Index: zone/perlparser.cpp
===================================================================
--- zone/perlparser.cpp	(revision 403)
+++ zone/perlparser.cpp	(working copy)
@@ -2416,6 +2416,37 @@
 	XSRETURN_EMPTY;
 }
 
+XS(XS__MerchantSetItem);
+XS(XS__MerchantSetItem) {
+	dXSARGS;
+	if (items != 2 && items != 3)
+		Perl_croak(aTHX_ "Usage: MerchantSetItem(NPCid, itemid [, quantity])");
+
+	int32 NPCid = (int)SvUV(ST(0));
+	int32 itemid = (int)SvUV(ST(1));
+	int32 quantity = 0;
+	if (items == 3)
+		quantity = (int)SvUV(ST(2));
+
+	quest_manager.MerchantSetItem(NPCid, itemid, quantity);
+
+	XSRETURN_EMPTY;
+}
+
+XS(XS__MerchantCountItem);
+XS(XS__MerchantCountItem) {
+	dXSARGS;
+	if (items != 2)
+		Perl_croak(aTHX_ "Usage: MerchantCountItem(NPCid, itemid)");
+
+	int32 NPCid = (int)SvUV(ST(0));
+	int32 itemid = (int)SvUV(ST(1));
+	int32 quantity = quest_manager.MerchantCountItem(NPCid, itemid);
+
+	XSRETURN_UV(quantity);
+}
+
+
 /*
 This is the callback perl will look for to setup the
 quest package's XSUBs
@@ -2584,12 +2615,11 @@
 		newXS(strcpy(buf, "modifynpcstat"), XS__ModifyNPCStat, file);
         newXS(strcpy(buf, "collectitems"), XS__collectitems, file);
 		newXS(strcpy(buf, "updatespawntimer"), XS__UpdateSpawnTimer, file);
+		newXS(strcpy(buf, "MerchantSetItem"), XS__MerchantSetItem, file);
+		newXS(strcpy(buf, "MerchantCountItem"), XS__MerchantCountItem, file);
 
 	XSRETURN_YES;
 }
 
-
-
-
 #endif
 #endif
Index: zone/questmgr.cpp
===================================================================
--- zone/questmgr.cpp	(revision 403)
+++ zone/questmgr.cpp	(working copy)
@@ -1774,3 +1774,44 @@
 		safe_delete(pack);
 	}
 }
+
+// used to set the number of an item in the selected merchant's temp item list.  Defaults to zero if no quantity is specified.
+void QuestManager::MerchantSetItem(int32 NPCid, int32 itemid, int32 quantity) {
+	Mob* merchant = entity_list.GetMobByNpcTypeID(NPCid);
+	
+	if (merchant == 0 || !merchant->IsNPC() || (merchant->GetClass() != MERCHANT)) 
+		return;	// don't do anything if NPCid isn't a merchant
+	
+	const Item_Struct* item = NULL;
+	item = database.GetItem(itemid);
+	if (!item) return;		// if the item id doesn't correspond to a real item, do nothing
+	
+	zone->SaveTempItem(merchant->CastToNPC()->MerchantType, NPCid, itemid, quantity);
+}
+
+int32 QuestManager::MerchantCountItem(int32 NPCid, int32 itemid) {
+	Mob* merchant = entity_list.GetMobByNpcTypeID(NPCid);
+	
+	if (merchant == 0 || !merchant->IsNPC() || (merchant->GetClass() != MERCHANT))
+		return 0;	// if it isn't a merchant, it doesn't have any items
+	
+	const Item_Struct* item = NULL;
+	item = database.GetItem(itemid);
+	if (!item) return 0;		// likewise, if it isn't a valid item, the merchant doesn't have any
+
+	// look for the item in the merchant's temporary list
+	std::list<TempMerchantList> MerchList = zone->tmpmerchanttable[NPCid];
+	std::list<TempMerchantList>::const_iterator itr;
+	TempMerchantList ml;
+	int32 Quant = 0;
+		
+	for(itr = MerchList.begin(); itr != MerchList.end(); itr++){
+		ml = *itr;
+		if (ml.item == itemid) {	// if this is the item we're looking for
+			Quant = ml.charges;
+			break;
+		}
+	}
+
+	return Quant;	// return the quantity of itemid (0 if it was never found)
+}
\ No newline at end of file
Index: zone/questmgr.h
===================================================================
--- zone/questmgr.h	(revision 403)
+++ zone/questmgr.h	(working copy)
@@ -194,6 +194,9 @@
 	void CreateGroundObject(int32 itemid, float x, float y, float z, float heading, int32 decay_time = 300000);
 	void ModifyNPCStat(const char *identifier, const char *newValue);
 	void UpdateSpawnTimer(int32 id, int32 newTime);
+
+	void MerchantSetItem(int32 NPCid, int32 itemid, int32 quantity = 0);
+	int32 MerchantCountItem(int32 NPCid, int32 itemid);
 	
 	//not in here because it retains perl types
 	//thing ChooseRandom(array_of_things)
Reply With Quote