示例#1
0
P_ITEM cCharStuff::AddRandomLoot(P_ITEM pBackpack, char * lootlist)
{
	char sect[512];
	int i,j, storeval,loopexit=0;
	P_ITEM retitem = NULL;
	storeval=-1;
	i=0; j=0;

	sprintf(sect, "LOOTLIST %s", lootlist);
	
	Script *pScpBase=i_scripts[npc_script];
	Script *pScp=pScpBase->Select(sect,custom_npc_script);
	if (!pScp) return NULL;

	loopexit=0;
	do
	{
		pScp->NextLine();
		if (script1[0]!='}')
		{
			i++; // Count number of entries on list.
		}
	} while ( (script1[0]!='}') && (++loopexit < MAXLOOPS) );
	pScp->Close();

	if(i>0)
	{
		i=rand()%(i);
		pScp=pScpBase->Select(sect,custom_npc_script);

		loopexit=0;
		do
		{
			pScp->NextLine();
			if (script1[0]!='}')
			{
				if(j==i)
				{
					storeval=str2num(script1);	//script1 = ITEM#

					scpMark m=pScp->Suspend();
					retitem = Targ->AddMenuTarget(-1, 0, storeval);
					pScp->Resume(m);

					if(retitem!=NULL)
					{
						retitem->pos.x=50+(rand()%80);
						retitem->pos.y=50+(rand()%80);
						retitem->pos.z=9;
						retitem->SetContSerial(pBackpack->serial);
					}
					break;;    
				}
				else j++;
			}
		}	while ( (script1[0]!='}') && (++loopexit < MAXLOOPS) );
		pScp->Close();
	}
	return retitem;
}
示例#2
0
P_ITEM cChar::GetBankBox( short banktype )			
{
	P_ITEM pi;
	unsigned int ci=0;
	vector<SERIAL> vecContainer = contsp.getData(serial);
	for ( ci = 0; ci < vecContainer.size(); ci++)
	{
		pi = FindItemBySerial(vecContainer[ci]);
		if (pi->type == 1 && pi->morex == 1)
			if ( banktype == 1 && pi->morez == 123 && SrvParams->useSpecialBank()) 
				return pi;
			else if ( banktype != 1 || !SrvParams->useSpecialBank())
				return pi;
	}
	// If we reach this point, bankbox wasn't found == wasn't created yet.

	sprintf((char*)temp, "%s's bank box.", name.c_str());
	UOXSOCKET s = calcSocketFromChar(this);
	pi = Items->SpawnItem(this, 1, (char*)temp, 0, 0x09AB, 0, 0);
	if(pi == NULL) 
		return NULL;
	pi->layer=0x1d;
	pi->SetOwnSerial(this->serial);
	pi->SetContSerial(this->serial);
	pi->morex=1;
	if(SrvParams->useSpecialBank() && banktype == 1)//AntiChrist - Special Bank
		pi->morey=123;//gold only bank
	pi->type=1;
	if (s != -1)
		wearIt(s, pi);

	return pi;
}
// Name:	item_bounce3
// Purpose:	holds some statements that were COPIED some 50 times
// Remarks:	temporary functions to revamp the 30 occurences of the 'bouncing bugfix'
// History:	init Duke, 10.8.2000
static void item_bounce3(const P_ITEM pi)
{
	pi->SetContSerial(pi->oldcontserial);
	pi->pos.x=pi->oldx;
	pi->pos.y=pi->oldy;
	pi->pos.z=pi->oldz;
	pi->layer=pi->oldlayer;
	pi->flags.isBeeingDragged=false;
	P_CHAR pc = FindCharBySerial(pi->oldcontserial);

	if (pi->layer > 0 && pc != NULL)
	{
		pc->st += pi->st2;
		pc->chgDex(pi->dx2);
		pc->in += pi->in;
	}
}
示例#4
0
P_CHAR cCharStuff::AddNPC(int s, P_ITEM pi_i, int npcNum, int x1, int y1, signed char z1)
{
	int tmp, z, lovalue, hivalue;
	int k=0, xos=0, yos=0, lb;
	char sect[512];
	int haircolor = -1; //(we need this to remember the haircolor)
	short postype;				// determines how xyz of the new NPC are set, see below
	short fx1,fx2,fy1,fy2,fz1;	// temp. hold the rectangle or circle for npcwander from script
	fx1=fx2=fy1=fy2=fz1=0;

	if (x1 > 0 && y1 > 0)
 		postype = 3;	// take position from parms
	else if ( s != -1 && pi_i == NULL)
		postype = 2;	// take position from socket's buffer
	else if ( s == -1 && pi_i != NULL)
		postype = 1;	// take position from items[i]
	else
	{
		clConsole.send("ERROR: bad parms in call to AddNPC\n");
		return NULL;
	}

	P_ITEM pBackpack = NULL;
	P_ITEM retitem = NULL;
	P_ITEM shoppack1 = NULL;
	P_ITEM shoppack2 = NULL;
	P_ITEM shoppack3 = NULL;
	//
	// First things first...lets find out what NPC# we should spawn
	//
	Script *pScpBase=i_scripts[npc_script];
	sprintf(sect, "NPC %i", npcNum);
	Script *pScp=pScpBase->Select(sect,custom_npc_script);
	if (!pScp) return NULL;
	
	unsigned long loopexit=0;
	do
	{
		pScp->NextLineSplitted();
		if (script1[0]!='}')
		{
			if (!(strcmp("NPCLIST", (char*)script1)))
			{
				npcNum = Npcs->getRandomNPC((char*)script2);
				sprintf(sect, "NPC %i", npcNum);
				break;
			}
		}
	} while ( (script1[0]!='}') && (++loopexit < MAXLOOPS) );

	pScp->Close();

	//
	// Now lets spawn him/her
	//
	P_CHAR pc_c = Npcs->MemCharFree();
	if ( pc_c == NULL )
		return NULL;
	pc_c->Init();
	

	pc_c->setPriv(0x10);
	pc_c->npc=1;
	pc_c->att=1;
	pc_c->def=1;
	pc_c->spawnserial = INVALID_SERIAL;
	
	pScp=pScpBase->Select(sect,custom_npc_script);
	if (!pScp)
	{
		Npcs->DeleteChar(pc_c);
		return NULL;
	}

	loopexit=0;
	do
	{
		pScp->NextLineSplitted();

		if (script1[0]!='}') {
			switch(script1[0])
			{
			case 'A':
			case 'a':
			if (!strcmp("ALCHEMY",(char*)script1))		pc_c->baseskill[ALCHEMY] = getstatskillvalue((char*)script2);
			else if (!strcmp("ANATOMY",(char*)script1))		pc_c->baseskill[ANATOMY] = getstatskillvalue((char*)script2);
			else if (!strcmp("ARCHERY",(char*)script1))		pc_c->baseskill[ARCHERY] = getstatskillvalue((char*)script2);
			else if (!strcmp("ARMSLORE",(char*)script1))		pc_c->baseskill[ARMSLORE] = getstatskillvalue((char*)script2);
			else if (!strcmp("ANIMALLORE",(char*)script1))	pc_c->baseskill[ANIMALLORE] = getstatskillvalue((char*)script2);
			break;

			case 'B':
			case 'b':
			if (!strcmp("BACKPACK", (char*)script1))
			{
				if (pBackpack == NULL)
				{
					scpMark m=pScp->Suspend();
					pBackpack = Items->SpawnItem(-1, pc_c,1,"Backpack",0,0x0E,0x75,0,0,0);
					if(pBackpack == NULL)
					{
						Npcs->DeleteChar(pc_c);
						return NULL;
					}
					pc_c->packitem = pBackpack->serial;
					pBackpack->pos.x=0;
					pBackpack->pos.y=0;
					pBackpack->pos.z=0;
					pBackpack->SetContSerial(pc_c->serial);
					pBackpack->layer=0x15;
					pBackpack->type=1;
					pBackpack->dye=1;
					
					retitem = pBackpack;
					pScp->Resume(m);
					strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
				}
			}
			else if (!strcmp("BEGGING",(char*)script1))			pc_c->baseskill[BEGGING] = getstatskillvalue((char*)script2);
			else if (!strcmp("BLACKSMITHING",(char*)script1))	pc_c->baseskill[BLACKSMITHING] = getstatskillvalue((char*)script2);
			else if (!strcmp("BOWCRAFT",(char*)script1))			pc_c->baseskill[BOWCRAFT] = getstatskillvalue((char*)script2);
			break;

			case 'C':
			case 'c':

			if (!strcmp("COLOR",(char*)script1)) {
				if (retitem != NULL)
				{
					retitem->color = hex2num(script2);
				}
			}
			else if (!strcmp("CARVE",(char*)script1)) pc_c->carve=str2num(script2);
			else if (!strcmp("CAMPING",(char*)script1)) pc_c->baseskill[CAMPING] = getstatskillvalue((char*)script2);
			else if (!strcmp("CARPENTRY",(char*)script1)) pc_c->baseskill[CARPENTRY] = getstatskillvalue((char*)script2);
			else if (!strcmp("CARTOGRAPHY",(char*)script1)) pc_c->baseskill[CARTOGRAPHY] = getstatskillvalue((char*)script2);
			else if (!strcmp("CANTRAIN",(char*)script1)) pc_c->cantrain=true;
			else if (!strcmp("COOKING",(char*)script1)) pc_c->baseskill[COOKING] = getstatskillvalue((char*)script2);
			else if (!strcmp("COLORMATCHHAIR",(char*)script1))
			{
				if (retitem != NULL && haircolor!=-1)
				{
					retitem->color = (haircolor);
				}
			}
			else if (!strcmp("COLORLIST",(char*)script1))
			{
				scpMark m=pScp->Suspend();
				unsigned short storeval = addrandomcolor(pc_c, (char*)script2);
				if (retitem != NULL)
				{
					retitem->color = storeval;
				}
				pScp->Resume(m);
				strcpy((char*)script1, "DUMMY"); // To prevent accidental exit of loop.
			}
			break;

			case 'D':
			case 'd':

			if (!strcmp("DIRECTION",(char*)script1)) {
				if (!strcmp("NE",(char*)script2)) pc_c->dir=1;
				else if (!strcmp("E",(char*)script2)) pc_c->dir=2;
				else if (!strcmp("SE",(char*)script2)) pc_c->dir=3;
				else if (!strcmp("S",(char*)script2)) pc_c->dir=4;
				else if (!strcmp("SW",(char*)script2)) pc_c->dir=5;
				else if (!strcmp("W",(char*)script2)) pc_c->dir=6;
				else if (!strcmp("NW",(char*)script2)) pc_c->dir=7;
				else if (!strcmp("N",(char*)script2)) pc_c->dir=0;
			}
			else if (!strcmp("DEX",(char*)script1) || !strcmp("DEXTERITY",(char*)script1)) 
			{
				pc_c->setDex(getstatskillvalue((char*)script2));
				pc_c->stm = pc_c->realDex();
			}
			else if (!strcmp("DEF",(char*)script1)) pc_c->def = getstatskillvalue((char*)script2);
			else if (!strcmp("DETECTINGHIDDEN",(char*)script1)) pc_c->baseskill[DETECTINGHIDDEN] = getstatskillvalue((char*)script2);
			else if (!strcmp("DAMAGE",(char*)script1) || !strcmp("ATT",(char*)script1)) {
				gettokennum((char*)script2, 0);
				lovalue=str2num(gettokenstr);
				gettokennum((char*)script2, 1);
				hivalue=str2num(gettokenstr);
				pc_c->lodamage = lovalue;
				pc_c->hidamage = lovalue;
				if(hivalue) {
					pc_c->hidamage = hivalue;
				}
			}
			break;

			case 'E':
			case 'e':

			if (!(strcmp("EMOTECOLOR",(char*)script1))) {
				pc_c->emotecolor = (hex2num(script2));
			}
			else if (!strcmp("ENTICEMENT",(char*)script1)) pc_c->baseskill[ENTICEMENT] = getstatskillvalue((char*)script2);
			else if (!strcmp("EVALUATINGINTEL",(char*)script1)) pc_c->baseskill[EVALUATINGINTEL] = getstatskillvalue((char*)script2);
			break;

			case 'F':
			case 'f':

			if (!strcmp("FISHING",(char*)script1)) pc_c->baseskill[FISHING] = getstatskillvalue((char*)script2);
			else if (!strcmp("FORENSICS",(char*)script1)) pc_c->baseskill[FORENSICS] = getstatskillvalue((char*)script2);
			else if (!strcmp("FX1",(char*)script1)) fx1=str2num(script2);  // new NPCWANDER implementation
			else if (!strcmp("FX2",(char*)script1)) fx2=str2num(script2);
			else if (!strcmp("FLEEAT",(char*)script1)) pc_c->fleeat=str2num(script2);
			else if (!strcmp("FAME",(char*)script1)) pc_c->fame=str2num(script2);
			else if (!strcmp("FENCING",(char*)script1)) pc_c->baseskill[FENCING] = getstatskillvalue((char*)script2);
			else if (!strcmp("FY1",(char*)script1)) fy1=str2num(script2);
			else if (!strcmp("FY2",(char*)script1)) fy2=str2num(script2);
			else if (!strcmp("FZ1",(char*)script1)) fz1=str2num(script2);
			break;

			case 'G':
			case 'g':

			if (!strcmp("GOLD", (char*)script1))
			{
				if (pBackpack != NULL)
				{ 
					scpMark m=pScp->Suspend();
					P_ITEM pGold = Items->SpawnItem(pc_c,1,"#",1,0x0EED,0,1);
					if(!pGold)
					{
						Npcs->DeleteChar(pc_c);
						return NULL;
					}
					pScp->Resume(m);

					pGold->priv|=0x01;
					gettokennum((char*)script2, 0);
					lovalue=str2num(gettokenstr);
					gettokennum((char*)script2, 1);
					hivalue=str2num(gettokenstr);
					if (hivalue==0)
					{
						if (lovalue/2!=0) pGold->amount=lovalue/2 + (rand()%(lovalue/2));
						else pGold->amount=0;
					} else
					{
						if (hivalue-lovalue!=0) pGold->amount=lovalue + (rand()%(hivalue-lovalue));
						else pGold->amount=lovalue;
					}
				}
				else
					clConsole.send("Warning: Bad NPC Script %d with problem no backpack for gold.\n", npcNum);
			}
			break;

			case 'H':
			case 'h':

			if (!strcmp("HEALING",(char*)script1)) pc_c->baseskill[HEALING] = getstatskillvalue((char*)script2);
			else if (!strcmp("HIDAMAGE",(char*)script1)) pc_c->hidamage=str2num(script2);
			else if (!strcmp("HERDING",(char*)script1)) pc_c->baseskill[HERDING] = getstatskillvalue((char*)script2);
			else if (!strcmp("HIDING",(char*)script1)) pc_c->baseskill[HIDING] = getstatskillvalue((char*)script2);
			else if (!strcmp("HAIRCOLOR",(char*)script1))
			{
				scpMark m=pScp->Suspend();
				
				if (retitem != NULL) // LB, ouple of bugfixes
				{
					haircolor=addrandomhaircolor(pc_c,(char*)script2);
					if (haircolor!=-1)
					{
						retitem->color = (haircolor);
					}
				}
				pScp->Resume(m);
				strcpy((char*)script1, "DUMMY"); // To prevent accidental exit of loop.
			}
			break;

			case 'I':
			case 'i':

			if (!strcmp("ID",(char*)script1)) 
			{
				tmp=hex2num(script2);
				pc_c->id1=tmp>>8;
				pc_c->id2=tmp%256;
				pc_c->xid = pc_c->id();
			}
			else if (!strcmp("ITEM",(char*)script1)) 
			{
				int storeval=str2num(script2);

				scpMark m=pScp->Suspend();
				retitem = Targ->AddMenuTarget(-1, 0, storeval);
				pScp->Resume(m);

				if ( retitem != NULL )
				{
					retitem->SetContSerial(pc_c->serial);
					if (retitem->layer==0) {
						clConsole.send("Warning: Bad NPC Script %d with problem item %d executed!\n", npcNum, storeval);
					}
				}
				strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
			}
			else if (!strcmp("INT",(char*)script1) || !strcmp("INTELLIGENCE",(char*)script1)) {
				pc_c->in  = getstatskillvalue((char*)script2);
				pc_c->in2 = pc_c->in;
				pc_c->mn  = pc_c->in;
			}
			//Done Handling Stats
			//Handle Skills
			else if (!strcmp("ITEMID",(char*)script1)) pc_c->baseskill[ITEMID] = getstatskillvalue((char*)script2);
			else if (!strcmp("INSCRIPTION",(char*)script1)) pc_c->baseskill[INSCRIPTION] = getstatskillvalue((char*)script2);
			break;
			
			case 'K':
			case 'k':
			if (!strcmp("KARMA",(char*)script1)) pc_c->karma=str2num(script2);
			break;

			case 'L':
			case 'l':

			if (!strcmp("LOOT",(char*)script1))
			{
				if (pBackpack != NULL)
				{
					scpMark m=pScp->Suspend();
					retitem = Npcs->AddRandomLoot(pBackpack, script2);
					pScp->Resume(m);

					strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
				} else
				{
					clConsole.send("Warning: Bad NPC Script %d with problem no backpack for loot.\n", npcNum);
				}
			}
			else if (!strcmp("LODAMAGE",(char*)script1)) pc_c->lodamage=str2num(script2);
			else if (!strcmp("LUMBERJACKING",(char*)script1)) pc_c->baseskill[LUMBERJACKING] = getstatskillvalue((char*)script2);
			else if (!strcmp("LOCKPICKING",(char*)script1)) pc_c->baseskill[LOCKPICKING] = getstatskillvalue((char*)script2);
			break;

			case 'M':
			case 'm':
			if ((!(strcmp("MACEFIGHTING",(char*)script1)))||(!(strcmp("SKILL41",(char*)script1)))) pc_c->baseskill[MACEFIGHTING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("MINING",(char*)script1)))||(!(strcmp("SKILL45",(char*)script1)))) pc_c->baseskill[MINING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("MAGERY",(char*)script1)))||(!(strcmp("SKILL25",(char*)script1)))) pc_c->baseskill[MAGERY] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("MAGICRESISTANCE",(char*)script1)))||(!(strcmp("RESIST",(char*)script1)))||(!(strcmp("SKILL26",(char*)script1)))) pc_c->baseskill[MAGICRESISTANCE] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("MUSICIANSHIP",(char*)script1)))||(!(strcmp("SKILL29",(char*)script1)))) pc_c->baseskill[MUSICIANSHIP] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("MEDITATION",(char*)script1)))||(!(strcmp("SKILL46",(char*)script1)))) pc_c->baseskill[MEDITATION] = getstatskillvalue((char*)script2);
			break;

			case 'N':
			case 'n':

			if (!(strcmp("NAME",(char*)script1))) pc_c->name = (char*)script2;
			else if (!(strcmp("NAMELIST", (char*)script1))) {
				scpMark m=pScp->Suspend();
				setrandomname(pc_c,(char*)script2);
				pScp->Resume(m);
				strcpy((char*)script1, "DUMMY"); // To prevent accidental exit of loop.
			}
			else if (!(strcmp((char*)script1, "NOTRAIN"))) pc_c->cantrain=false;
			else if (!(strcmp("NPCWANDER",(char*)script1))) pc_c->npcWander=str2num(script2);
			else if (!(strcmp("NPCAI",(char*)script1))) pc_c->npcaitype=hex2num(script2);
			break;

			case 'O':
			case 'o':
			if (!(strcmp("ONHORSE",(char*)script1))) pc_c->onhorse=true;
			break;

			case 'P':
			case 'p':

			if (!strcmp("PARRYING",(char*)script1)) pc_c->baseskill[PARRYING] = getstatskillvalue((char*)script2);
			else if (!(strcmp("PRIV1",(char*)script1))) pc_c->setPriv(str2num(script2));
			else if (!(strcmp("PRIV2",(char*)script1))) pc_c->priv2=str2num(script2);
			else if (!(strcmp("POISON",(char*)script1))) pc_c->poison=str2num(script2);
			else if ((!(strcmp("PEACEMAKING",(char*)script1)))||(!(strcmp("SKILL9",(char*)script1)))) pc_c->baseskill[PEACEMAKING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("PROVOCATION",(char*)script1)))||(!(strcmp("SKILL22",(char*)script1)))) pc_c->baseskill[PROVOCATION] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("POISONING",(char*)script1)))||(!(strcmp("SKILL30",(char*)script1)))) pc_c->baseskill[POISONING] = getstatskillvalue((char*)script2);
			else if (!(strcmp("PACKITEM",(char*)script1)))
			{
				if (pBackpack != NULL) 
				{
					int storeval=str2num(script2);

					scpMark m=pScp->Suspend();
					retitem = Targ->AddMenuTarget(-1, 0, storeval);
					pScp->Resume(m);

					if (retitem != NULL)
					{
						retitem->SetContSerial(pBackpack->serial);
						retitem->pos.x=50+(rand()%80);
						retitem->pos.y=50+(rand()%80);
						retitem->pos.z=9;
					}
					strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
				} else
				{
					clConsole.send("Warning: Bad NPC Script %d with problem no backpack for packitem.\n", npcNum);
				}
			}
			break;

			case 'R':
			case 'r':
			if (!(strcmp("RACE",(char*)script1))) pc_c->race=str2num(script2);
			else if (!(strcmp("REATTACKAT",(char*)script1))) pc_c->reattackat=str2num(script2);
			else if ((!(strcmp("REMOVETRAPS",(char*)script1)))||(!(strcmp("SKILL48",(char*)script1)))) pc_c->baseskill[REMOVETRAPS] = getstatskillvalue((char*)script2);
			else if (!(strcmp("RSHOPITEM",(char*)script1)))
			{
				if ( shoppack1 == NULL)
				{
					AllItemsIterator iterItems;
					for(iterItems.Begin(); !iterItems.atEnd(); iterItems++)
					{
						P_ITEM pz = iterItems.GetData();
						if (!pz->free)
						{
							if (pc_c->Wears(pz) &&
								pz->layer==0x1A)
							{
								shoppack1 = pz;
								break;
							}
						}
					}
					//if (shoppack1 == -1)
					  //LogError("Error creating shoppack1\n");
				}
				if ( shoppack1 != NULL )
				{
					int storeval=str2num(script2);

					scpMark m=pScp->Suspend();
					retitem = Targ->AddMenuTarget(-1, 0, storeval);
					pScp->Resume(m);

					if (retitem != NULL)
					{
						retitem->SetContSerial(shoppack1->serial);
						retitem->pos.x=50+(rand()%80);
						retitem->pos.y=50+(rand()%80);
						retitem->pos.z=9;
						if (retitem->name2 != "#") retitem->name = retitem->name2; // Item identified! -- by Magius(CHE)					}
					}
					strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
				} else
				{
					clConsole.send("Warning: Bad NPC Script %d with problem no shoppack1 for item.\n", npcNum);
				}
			}
			break;

			case 'S':
			case 's':

			if (!(strcmp("SKIN",(char*)script1))) 
			{
				pc_c->skin = pc_c->xskin = hex2num(script2);
			}
			else if (!(strcmp("SHOPKEEPER", (char*)script1))) 
			{
				scpMark m=pScp->Suspend();
				Commands->MakeShop(pc_c); 
				pScp->Resume(m);
			}
			else if (!(strcmp("SELLITEM",(char*)script1))) 
			{
				if (shoppack3 == NULL) 
				{
					AllItemsIterator iterItems;
					for(iterItems.Begin(); !iterItems.atEnd(); iterItems++) 
					{
						P_ITEM pz = iterItems.GetData();
						if (!pz->free)
						{
							if (pc_c->Wears(pz) && pz->layer==0x1C)
							{
								shoppack3 = pz;
								break;
							}
						}
					}
				}
				if ( shoppack3 != NULL ) 
				{
					int storeval=str2num(script2);

					scpMark m=pScp->Suspend();
					retitem = Targ->AddMenuTarget(-1, 0, storeval);
					pScp->Resume(m);

					if (retitem != NULL)
					{
						retitem->SetContSerial(shoppack3->serial);
						retitem->value=retitem->value/2;
						retitem->pos.x=50+(rand()%80);
						retitem->pos.y=50+(rand()%80);
						retitem->pos.z=9;
						if (retitem->name2 != "#") 
							retitem->name = retitem->name2; // Item identified! -- by Magius(CHE)					}
					}
					strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
				} else
				{
					clConsole.send("Warning: Bad NPC Script %d with problem no shoppack3 for item.\n", npcNum);
				}
			}
			else if (!(strcmp("SHOPITEM",(char*)script1)))
			{
				if ( shoppack2 == NULL )
				{
					AllItemsIterator iterItems;
					for (iterItems.Begin(); !iterItems.atEnd(); iterItems++)
					{
						P_ITEM pz = iterItems.GetData();
						if (!pz->free)
						{
							if (pc_c->Wears(pz) && pz->layer==0x1B)
							{
								shoppack2 = pz;
								break;
							}
						}
					}
				}
				if (shoppack2 != NULL)
				{
					int storeval = str2num(script2);

					scpMark m = pScp->Suspend();
					retitem = Targ->AddMenuTarget(-1, 0, storeval);
					pScp->Resume(m);

					if ( retitem != NULL)
					{
						retitem->SetContSerial(shoppack2->serial);
						retitem->pos.x=50+(rand()%80);
						retitem->pos.y=50+(rand()%80);
						retitem->pos.z=9;
						if (retitem->name2 != "#") 
							retitem->name = retitem->name2; // Item identified! -- by Magius(CHE)					}
					}
					strcpy((char*)script1, "DUMMY"); // Prevents unexpected matchups...
				} else
				{
					clConsole.send("Warning: Bad NPC Script %d with problem no shoppack2 for item.\n", npcNum);
				}
			}
			else if (!(strcmp("SPATTACK",(char*)script1))) pc_c->spattack=str2num(script2);
			else if (!(strcmp("SPEECH",(char*)script1))) pc_c->speech=str2num(script2);
			else if (!(strcmp("SPLIT",(char*)script1))) pc_c->split=str2num(script2);
			else if ((!(strcmp("STR",(char*)script1)))||(!(strcmp("STRENGTH",(char*)script1)))) {
				pc_c->st  = getstatskillvalue((char*)script2);
				pc_c->st2 = pc_c->st;
				pc_c->hp  = pc_c->st;
			}
			else if (!(strcmp("SPLITCHANCE",(char*)script1))) pc_c->splitchnc=str2num(script2);
			else if (!(strcmp("SAYCOLOR",(char*)script1))) 			pc_c->saycolor = static_cast<UI16>(hex2num(script2));
			else if (!(strcmp("SPADELAY",(char*)script1))) pc_c->spadelay=str2num(script2);
			else if ((!(strcmp("SPIRITSPEAK",(char*)script1)))||(!(strcmp("SKILL32",(char*)script1)))) pc_c->baseskill[SPIRITSPEAK] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("STEALTH",(char*)script1)))||(!(strcmp("SKILL47",(char*)script1)))) pc_c->baseskill[STEALTH] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("SWORDSMANSHIP",(char*)script1)))||(!(strcmp("SKILL40",(char*)script1)))) pc_c->baseskill[SWORDSMANSHIP] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("SNOOPING",(char*)script1)))||(!(strcmp("SKILL28",(char*)script1)))) pc_c->baseskill[SNOOPING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("STEALING",(char*)script1)))||(!(strcmp("SKILL33",(char*)script1)))) pc_c->baseskill[STEALING] = getstatskillvalue((char*)script2);
			else if (!(strcmp("SKINLIST",(char*)script1)))
			{
				scpMark m=pScp->Suspend();
				pc_c->xskin = pc_c->skin = addrandomcolor(pc_c,(char*)script2);
				pScp->Resume(m);
				strcpy((char*)script1, "DUMMY"); // To prevent accidental exit of loop.
			}
			else if (!(strcmp("SKILL", (char*)script1)))
			{
				gettokennum((char*)script2, 0);
				z=str2num(gettokenstr);
				gettokennum((char*)script2, 1);
				pc_c->baseskill[z]=str2num(gettokenstr);
			}

            else if (!(strcmp("STABLEMASTER",(char*)script1))) pc_c->npc_type=1;
			break;

			case 'T':
			case 't':
			if (!(strcmp("TITLE",(char*)script1))) pc_c->title = script2;
			else if ((!(strcmp("TOTAME", (char*)script1)))||(!(strcmp("TAMING", (char*)script1)))) pc_c->taming=str2num(script2);
			else if (!(strcmp("TRIGGER",(char*)script1)))	pc_c->trigger=str2num(script2);
			else if (!(strcmp("TRIGWORD",(char*)script1)))	pc_c->trigword = (char*)script2;
			else if ((!(strcmp("TACTICS",(char*)script1)))||(!(strcmp("SKILL27",(char*)script1)))) pc_c->baseskill[TACTICS] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("TAILORING",(char*)script1)))||(!(strcmp("SKILL34",(char*)script1)))) pc_c->baseskill[TAILORING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("TAMING",(char*)script1)))||(!(strcmp("SKILL35",(char*)script1)))) pc_c->baseskill[TAMING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("TASTEID",(char*)script1)))||(!(strcmp("SKILL36",(char*)script1)))) pc_c->baseskill[TASTEID] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("TINKERING",(char*)script1)))||(!(strcmp("SKILL37",(char*)script1)))) pc_c->baseskill[TINKERING] = getstatskillvalue((char*)script2);
			else if ((!(strcmp("TRACKING",(char*)script1)))||(!(strcmp("SKILL38",(char*)script1)))) pc_c->baseskill[TRACKING] = getstatskillvalue((char*)script2);
			break;

			case 'V':
			case 'v':
			if (!(strcmp("VALUE",(char*)script1))) if (retitem != NULL) retitem->value=(str2num(script2));
			else if (!strcmp("VETERINARY",(char*)script1)) pc_c->baseskill[VETERINARY] = getstatskillvalue((char*)script2);
			break;
			
			case 'W':
			case 'w':
			if ((!(strcmp("WRESTLING",(char*)script1)))||(!(strcmp("SKILL43",(char*)script1)))) pc_c->baseskill[WRESTLING] = getstatskillvalue((char*)script2);
			break;

			default:
				clConsole.send("Warning: Fall out of switch statement in npcs.cpp AddNPC()\n");
			}
			
			//Done Handling Skills
			//Handle Extras

			//Done Handling Obsolete Stuff
			//--------------- DONE NEW STAT & SKILL FORMAT ---------------------
      }
示例#5
0
void cTrade::buyaction(int s)
{
	char clearmsg[8];
	int clear, i, j;
	P_ITEM buyit[256];
	int amount[512];
	int layer[512];
	int playergoldtotal;
	int goldtotal;
	int itemtotal;
	int soldout;
	int tmpvalue=0; // Fixed for adv trade system -- Magius(CHE) §
//	CHARACTER cc=currchar[s];
	P_CHAR pc_currchar = currchar[s];
	P_ITEM pi_pack = Packitem(pc_currchar);
	if (pi_pack == NULL)
		return; //LB no player-pack - no buy action possible - and no crash too ;-)
	P_CHAR npc = FindCharBySerial(calcserial(buffer[s][3], buffer[s][4], buffer[s][5], buffer[s][6]));

	if (npc <= 0) return;

	clear=0;
	goldtotal=0;
	soldout=0;
	itemtotal=(((256*(buffer[s][1]))+buffer[s][2])-8)/7;
	if (itemtotal>256) return; //LB

	for(i = 0; i < itemtotal; i++)
	{
		layer[i]=buffer[s][8+(7*i)];
		buyit[i] = FindItemBySerial(calcserial(buffer[s][8+(7*i)+1], buffer[s][8+(7*i)+2], buffer[s][8+(7*i)+3], buffer[s][8+(7*i)+4]));
		amount[i]=(256*(buffer[s][8+(7*i)+5]))+buffer[s][8+(7*i)+6];

		if (buyit[i] != NULL)
		{
			buyit[i]->rank=10;
			// Fixed for adv trade system -- Magius(CHE) §
			tmpvalue = buyit[i]->value;
			tmpvalue = calcValue(buyit[i], tmpvalue);
			if (SrvParams->trade_system()==1)
				tmpvalue = calcGoodValue(pc_currchar, buyit[i], tmpvalue,0);
			goldtotal += (amount[i]*tmpvalue);
			// End Fix for adv trade system -- Magius(CHE) §
		}
	}

	bool useBank;
	useBank = (goldtotal >= SrvParams->checkBank() );

	if( useBank )
		playergoldtotal = GetBankCount( pc_currchar, 0x0EED );
	else
		playergoldtotal = pc_currchar->CountGold();

	if ((playergoldtotal>=goldtotal)||(pc_currchar->isGM()))
	{
		for (i = 0; i < itemtotal; i++)
		{
			if (buyit[i] != NULL)
			{
				if (buyit[i]->amount < amount[i])
				{
					soldout = 1;
				}
			}
		}
		if (soldout)
		{
			npctalk(s, npc, "Alas, I no longer have all those goods in stock. Let me know if there is something else thou wouldst buy.",0);
			clear = 1;
		}
		else
		{
			if (pc_currchar->isGM())
			{
				sprintf((char*)temp, "Here you are, %s. Someone as special as thee will receive my wares for free of course.", pc_currchar->name.c_str());
			}
			else
			{
				if(useBank)
				{
					sprintf((char*)temp, "Here you are, %s. %d gold coin%s will be deducted from your bank account.  I thank thee for thy business.",
					pc_currchar->name.c_str(), goldtotal, (goldtotal==1) ? "" : "s");
				    goldsfx(s, goldtotal);
				}
			    else
				{
				    sprintf((char*)temp, "Here you are, %s.  That will be %d gold coin%s.  I thank thee for thy business.",
					pc_currchar->name.c_str(), goldtotal, (goldtotal==1) ? "" : "s");
				    goldsfx(s, goldtotal);	// Dupois, SFX for gold movement. Added Oct 08, 1998
				}
			}
			npctalkall(npc, (char*)temp, 0);
			npcaction(npc, 0x20);		// bow (Duke, 17.3.2001)

			clear = 1;
			if( !(pc_currchar->isGM() ) )
			{
				if( useBank )
					DeleBankItem( pc_currchar, 0x0EED, 0, goldtotal );
				else
					delequan( pc_currchar, 0x0EED, goldtotal, NULL );
			}
			for (i=0;i<itemtotal;i++)
			{
				P_ITEM pi = buyit[i];
				if (pi != NULL)
				{
					if (pi->amount>amount[i])
					{
						if (pi->pileable)
						{
							Commands->DupeItem(s, buyit[i], amount[i]);
						}
						else
						{
							for (j=0;j<amount[i];j++)
							{
								Commands->DupeItem(s, buyit[i], 1);
							}
						}
						pi->amount-=amount[i];
						pi->restock+=amount[i];
					}
					else
					{
						switch(layer[i])
						{
						case 0x1A:
							if (pi->pileable)
							{
								Commands->DupeItem(s, buyit[i], amount[i]);
							}
							else
							{
								for (j=0;j<amount[i];j++)
								{
									Commands->DupeItem(s, buyit[i], 1);
								}
							}
							pi->amount=pi->amount-amount[i];
							pi->restock=pi->restock+amount[i];
							break;
						case 0x1B:
							if (pi->pileable)
							{
								pi->SetContSerial(pi_pack->serial);
								RefreshItem(buyit[i]);//AntiChrist
							}
							else
							{
								for (j=0;j<amount[i]-1;j++)
								{
									Commands->DupeItem(s, buyit[i], 1);
								}
								pi->SetContSerial(pi_pack->serial);
								pi->amount = 1;
								RefreshItem(buyit[i]);//AntiChrist
							}
							break;
						default:
							clConsole.send("ERROR: Fallout of switch statement without default. wolfpack.cpp, buyaction()\n"); //Morrolan
						}
					}
				}
			}
		}
	}
	else
	{
		npctalkall(npc, "Alas, thou dost not possess sufficient gold for this purchase!",0);
	}

	if (clear)
	{
		clearmsg[0]=0x3B;
		clearmsg[1]=0x00;
		clearmsg[2]=0x08;
		clearmsg[3]=buffer[s][3];
		clearmsg[4]=buffer[s][4];
		clearmsg[5]=buffer[s][5];
		clearmsg[6]=buffer[s][6];
		clearmsg[7]=0x00;
		Xsend(s, clearmsg, 8);
	}
	Weight->NewCalc(pc_currchar);	// Ison 2-20-99
	statwindow(s, pc_currchar);
}
static bool ItemDroppedOnChar(P_CLIENT ps, PKGx08 *pp, P_ITEM pi)
{
	UOXSOCKET s=ps->GetSocket();
	CHARACTER cc=ps->GetCurrChar();
	P_CHAR pc_currchar = MAKE_CHARREF_LRV(cc,true);
	P_CHAR pTC=FindCharBySerial(pp->Tserial);	// the targeted character
	if (!pTC) return true;

	if (DEREF_P_CHAR(pTC)!=DEREF_P_CHAR(pc_currchar))
	{
		if (pTC->isNpc())
		{
			if(!pTC->isHuman())						
			{
				ItemDroppedOnPet( ps, pp, pi);
			}
			else	// Item dropped on a Human character
			{
				// Item dropped on a Guard (possible bounty quest)
				if( ( pTC->isNpc() ) && ( pTC->npcaitype == 4 ) )
				{
					if (!ItemDroppedOnGuard( ps, pp, pi) )
					{
						Sndbounce5(s);
						if (ps->IsDragging())
						{
							ps->ResetDragging();
							item_bounce5(s,pi);
						}
					}
					return true;
				}
				if ( pTC->npcaitype == 5 )
				{
					if (!ItemDroppedOnBeggar( ps, pp, pi))
					{
						Sndbounce5(s);
						if (ps->IsDragging())
						{
							ps->ResetDragging();
							item_bounce5(s,pi);
						}
					}
					return true;
				}
				if ( pTC->npcaitype == 8 )
				{
					if (!ItemDroppedOnBanker( ps, pp, pi))
					{
						Sndbounce5(s);
						if (ps->IsDragging())
						{
							ps->ResetDragging();
							item_bounce5(s,pi);
						}
					}
					return true;
				}
				
				//This crazy training stuff done by Anthracks ([email protected])
				if(pc_currchar->trainer!=pTC->serial)
				{
					npctalk(s, DEREF_P_CHAR(pTC), "Thank thee kindly, but I have done nothing to warrant a gift.",0);
					Sndbounce5(s);
					if (ps->IsDragging())
					{
						ps->ResetDragging();
						item_bounce5(s,pi);
					}
					return true;
				}
				else // The player is training from this NPC
				{
					ItemDroppedOnTrainer( ps, pp, pi);
					return true;
				}
			}//if human or not
		}
		else // dropped on another player
		{
			// By Polygon: Avoid starting the trade if GM drops item on logged on char (crash fix)
			if ((pc_currchar->isGM()) && !online(DEREF_P_CHAR(pTC)))
			{
				// Drop the item in the players pack instead
				// Get the pack
				P_ITEM pack = Packitem(pTC);
				if (pack != NULL)	// Valid pack?
				{
					pack->AddItem(pi);	// Add it
					Weight->NewCalc(DEREF_P_CHAR(pTC));
				}
				else	// No pack, give it back to the GM
				{
					pack = Packitem(pc_currchar);
					if (pack != NULL)	// Valid pack?
					{
						pack->AddItem(pi);	// Add it
						Weight->NewCalc(DEREF_P_CHAR(pc_currchar));
					}
					else	// Even GM has no pack?
					{
						// Drop it to it's feet
						pi->MoveTo(pc_currchar->pos.x, pc_currchar->pos.y, pc_currchar->pos.z);
						RefreshItem(pi);
					}
				}
			}
			else
			{
				P_ITEM pj = Trade->tradestart(s, DEREF_P_CHAR(pTC)); //trade-stuff
				pi->SetContSerial(pj->serial);
				pi->pos.x=30;
				pi->pos.y=30;
				pi->pos.z=9;
				SndRemoveitem(pi->serial);
				RefreshItem(pi);
			}
		}


	}
	else // dumping stuff to his own backpack !
	{
		ItemDroppedOnSelf( ps, pp, pi);
	}
	return true;
}
void cDragdrop::get_item(P_CLIENT ps) // Client grabs an item
{
	int npc=-1, amount, update = 0, serial;
	UOXSOCKET s = ps->GetSocket();
	int cc = ps->GetCurrChar();
	P_CHAR pc_currchar = MAKE_CHARREF_LR(cc);
	
	
	serial = calcserial(buffer[s][1], buffer[s][2], buffer[s][3], buffer[s][4]);
	if (serial == INVALID_SERIAL || buffer[s][1] < 0x40)
		return;	// landscape or a character
	P_ITEM pi = FindItemBySerial(serial);
	if (pi == NULL)
		return;
	
	pc_currchar->disturbMed(s); // Meditation
	
	// Zippy's stealing changes  
	P_ITEM px = pi;
	if (!px->isInWorld())  // Find character owning item
	{
		unsigned long loopexit = 0;
		do  // Find character owning item
		{
			if (isCharSerial(px->contserial))
			{
				npc = calcCharFromSer(px->contserial);
			}
			else  // its an item
			{
				if (px->isInWorld())
				{
					npc=-1;
					break;
				}
				px = FindItemBySerial(px->contserial);
				// ANTICHRIST -- SECURE TRADE FIX
				if (px != NULL) // LB overwriting x is essential here, dont change it!!!
				{
					if (px->layer == 0 && px->id() == 0x1E5E)
					{
						// Trade window???
						serial = calcserial(px->moreb1, px->moreb2, px->moreb3, px->moreb4);
						if (serial == INVALID_SERIAL)
							return;
						P_ITEM pi_z = FindItemBySerial(serial);
						if ( pi_z != NULL )
							if ((pi_z->morez || px->morez))
							{
								pi_z->morez = 0;
								px->morez = 0;
								sendtradestatus(pi_z, px);
							}
					}
					// Blackwinds Looting is crime implementation
					// changed slightly by Ripper
					if (px->corpse != 0 && !pc_currchar->Owns(px)) 
					{ 
						P_CHAR co = FindCharBySerial(px->ownserial);
						if (px->more2 == 1 && Guilds->Compare(DEREF_P_CHAR(pc_currchar), DEREF_P_CHAR(co)) == 0) 
						{ 
							pc_currchar->karma -= 5; 
							criminal(DEREF_P_CHAR(pc_currchar));
							sysmessage(s, "You lost some karma!"); 
						} 
						npc = 0;
					} // Criminal stuff
					if (px->corpse != 0)
						npc = 0;
				} // end if x!=-1
				
				if (px == NULL)
					npc = 0; 
			}
		} while ((npc==-1) &&(++loopexit < MAXLOOPS));
	}
	
	if (npc>0) // 0=corpse, hence >0 ..
	{
		if (!(pc_currchar->isGM()) && npc != DEREF_P_CHAR(pc_currchar) && ! pc_currchar->Owns(&chars[npc]))
		{// Own serial stuff by Zippy -^ Pack aniamls and vendors.
			bounce[1] = 0;
			Xsend(s, bounce, 2);
			if (ps->IsDragging())
			{
				ps->ResetDragging();
				item_bounce3(pi);
				pi->magic = 3;
			} 
			return;
		}
	}
	// End Zippy's change
	
	// Boats->
	if (px != NULL && npc!=-1)
	{
		if (px->multis>0)
			imultisp.remove(px->multis, px->serial);
		px->startDecay();
		// End Boats Change
		
		// AntiChrist -- for poisoned items
		if (px->layer>0)
		{
			chars[npc].removeItemBonus(px);	// remove BONUS STATS given by equipped special items
		}
		if ((px->trigon==1) && (px->layer != 0) && (px->layer != 15) && (px->layer < 19))// -Frazurbluu- Trigger Type 2 is my new trigger type *-
		{
			Trig->triggerwitem(s, pi, 1); // trigger is fired
		}	
	}
	if (pi != NULL)
	{
		if (pi->corpse != 1)
		{
			UpdateStatusWindow(s, pi);
			if (!pc_currchar->canPickUp(pi))
			{
				bounce[1] = 0;
				Xsend(s, bounce, 2);
				if (ps->IsDragging()) // only restore item if it got draggged before !!!
				{
					ps->ResetDragging();
					item_bounce4(s, pi);
				}
			}
			else
			{
				// AntiChrist bugfix for the bad bouncing bug ( disappearing items when bouncing )
				DRAGGED[s] = 1;
				
				pi->oldx = pi->pos.x;	// first let's save the position
				pi->oldy = pi->pos.y;
				pi->oldz = pi->pos.z;
				pi->oldcontserial = pi->contserial;	// then let's save the container
				pi->oldlayer = pi->layer;	// then the layer
				
				pi->layer = 0;
				if (!pi->isInWorld())
					soundeffect(s, 0x00, 0x57);
				if (pi->amount>1)
				{
					amount = (buffer[s][5] << 8) + buffer[s][6];
					if (amount>pi->amount)
						amount = pi->amount;
					if (amount < pi->amount)
					{
						P_ITEM pi_c = Items->MemItemFree();
						//	pi_c->Init(0);
#pragma note("Replace by a copy constructor before finishing items[]")
						memcpy(pi_c, pi, sizeof(cItem));  // Tauriel reduce code faster too
						pi_c->SetSerial(cItemsManager::getItemsManager().getUnusedSerial());

						pi_c->amount = pi->amount - amount;
						pi_c->SetContSerial(pi_c->contserial);
						pi_c->SetOwnSerial(pi_c->ownserial);
						pi_c->SetSpawnSerial(pi_c->spawnserial);
						
						statwindow(s,DEREF_P_CHAR(pc_currchar));
						RefreshItem(pi_c);//AntiChrist
					}
					
					if (pi->id() == 0x0EED) // gold coin
					{
						P_ITEM packnum = packitem(currchar[s]);
						if (packnum != NULL) // lb
							if (pi->contserial == packnum->serial)
								update = 1;
					}
					
					pi->amount = amount;
					
				}
				
			/*	int amt = 0, wgt; bool tooheavy=false;				
				wgt = (int)Weight->LockeddownWeight(pi, &amt, 0);
				if(pi->contserial>0)
				{
					if (( (pc_currchar->weight+wgt) > (pc_currchar->st*WEIGHT_PER_STR)+30)) // LB -> added: drop item if too heavy
					{
					  float res=float( (pc_currchar->weight+wgt) - ((pc_currchar->st*WEIGHT_PER_STR)+30))*2;
					  int diff = pc_currchar->st;
					  diff -= (int)res;
					  if (diff<=0 && !pc_currchar->isGM() )					   
					  {
						 tooheavy=true;						 						 

						 bounce[1] = 0;
						 Xsend(s, bounce, 2);
						 if (ps->IsDragging()) // only restore item if it got dragged before !!!
						 {
						   ps->ResetDragging();
						   item_bounce4(s, pi);
						 }
						 sysmessage(s, "you can't pick this up, this is too heavy");					 
						 return;
					 }
					}
				} 

                if (!tooheavy) pc_currchar->weight+=wgt;				   
				update = 1;	*/				

				// LB remark: drop item if too heavy is a good solution,
				// but there's still a small bug remaining.
				// added weight from items picked up, but not put to bp, pd,  in other words hold in ones hand, 
				// is NOT subtracted when being dropped again to ground/other chars/other chars' bp's.
				// but this bug doesnt show up becasue weight is re-calculated automatically all 10 secs.
				// without adding weight of the item curently carrying in hand.
				// a correct solutions need the weight of item in hand being stored
				// , added to auto-re-calculation all x-secs code, and being subtracted if dropped.
				// because it's now only happening for leight weight items, because heavy weight itms cant be picke up anymore
				// I haven't corrected this yet. 			
				
				// Tauriel remove item from world mapcells
				mapRegions->Remove(pi); // remove this item from a map cell				
				pi->pos.x = 0;
				pi->pos.y = 0;
				pi->pos.z = 0;
				
				pi->flags.isBeeingDragged=true;
				pi->SetContSerial(-1);
			
			
			}
		}
	} // end of if i!=-1
	if (update) statwindow(s, DEREF_P_CHAR(pc_currchar));
}
void pack_item(P_CLIENT ps, PKGx08 *pp) // Item is put into container
{
	int j, serial;
	bool abort=false;
	UOXSOCKET s=ps->GetSocket();
	CHARACTER cc=ps->GetCurrChar();
	P_CHAR pc_currchar = MAKE_CHARREF_LR(cc);
	
	serial=pp->Tserial;
	if(serial == INVALID_SERIAL) abort=true;
	const P_ITEM pCont= FindItemBySerial( serial );
	
	serial=pp->Iserial;
	if(serial == INVALID_SERIAL) abort=true;
	const P_ITEM pItem = FindItemBySerial( serial );
	
	if (pCont == NULL)
	{
		RefreshItem(pCont);//AntiChrist
		return;
	} 
	
	if (pItem == NULL || pCont == NULL) return; //LB
	pItem->flags.isBeeingDragged=false;

	if (pItem->id1>=0x40) 
	{ 
	   abort=true; // LB crashfix that prevents moving multi objcts in BP's
       sysmessage(s,"Hey, putting houses in your pack crashes your back and client!");
	}
	j=DEREF_P_CHAR(GetPackOwner(pCont));
	if (j>-1)
		if (chars[j].npcaitype==17 && chars[j].isNpc() && !pc_currchar->Owns(&chars[j]))
		{
			abort=true;
			sysmessage(s, "This aint your vendor!");				
		}

	if(abort)
	{//AntiChrist to preview item disappearing
		item_bounce6(ps,pItem);
		return;
	}

	if (pCont->layer==0 && pCont->id() == 0x1E5E &&
		pc_currchar->Wears(pCont))
	{
		// Trade window???
		serial=calcserial(pCont->moreb1, pCont->moreb2, pCont->moreb3, pCont->moreb4);
		if(serial == INVALID_SERIAL) return;
		P_ITEM pi_z = FindItemBySerial( serial );
		
		if (pi_z != NULL)
			if ((pi_z->morez || pCont->morez))
			{
				pi_z->morez=0;
				pCont->morez=0;
				sendtradestatus(pi_z, pCont);
			}
	}
	
	//
	//AntiChrist - Special Bank Stuff
	//
	//if morey==123  - gold only bank	
	//
	if(SrvParms->usespecialbank)//only if special bank is activated
	{
		if(pCont->morey==123 && pCont->morex==1 && pCont->type==1)
		{
			if ( pItem->id() == 0x0EED )
			{//if they're gold ok
				goldsfx(s, 2);
			} else
			{//if they're not gold..bounce on ground
				sysmessage(s,"You can only put golds in this bank box!");

				pItem->SetContSerial(-1);
				pItem->MoveTo(pc_currchar->pos.x,pc_currchar->pos.y,pc_currchar->pos.z);
				RefreshItem(pItem);//AntiChrist
				itemsfx(s,pItem->id());
				return;
			}
		}
	}
	
	//testing UOP Blocking Tauriel 1-12-99
	if (!pItem->isInWorld())
	{
		item_bounce6(ps,pItem);
		return;
	}
	
	if (!pc_currchar->canPickUp(pItem))
	{
		Sndbounce5(s);
		if (ps->IsDragging())
		{
			ps->ResetDragging();
			item_bounce3(pItem);
			if (pCont->id1>=0x40)
				senditem(s, pCont);
		}
		return;
	}
	// - Trash container
	if (pCont->type==87)
	{
		Items->DeleItem(pItem);
		sysmessage(s, "As you let go of the item it disappears.");
		return;
	}
	// - Spell Book
	if (pCont->type==9)
	{
		if (!IsSpellScroll72(pItem->id()))
		{
			sysmessage(s, "You can only place spell scrolls in a spellbook!");
			Sndbounce5(s);
			if (ps->IsDragging())
			{
				ps->ResetDragging();
				item_bounce3(pItem);
			}
			if (pCont->id1>=0x40)
				senditem(s, pCont);
			return;
		}
		P_ITEM pBackpack = Packitem(pc_currchar);
		if (pBackpack != NULL) // lb
		{
			if (!pc_currchar->Wears(pCont) &&
				(!(pCont->contserial==pBackpack->serial)) && (!(pc_currchar->canSnoop())))
			{
				sysmessage(s, "You cannot place spells in other peoples spellbooks.");
				item_bounce6(ps,pItem);
				return;
			}
			
			if(pItem->name[0]=='#')
				pItem->getName(temp2);
			else
				strcpy((char*)temp2,pItem->name);

			vector<SERIAL> vecContainer = contsp.getData(pCont->serial);
			for (unsigned int i = 0; i < vecContainer.size(); i++) // antichrist , bugfix for inscribing scrolls
			{
				P_ITEM pi = FindItemBySerial(vecContainer[i]);
				if (pi != NULL)
				{
					if(pi->name[0]=='#')
						pi->getName(temp);
					else
						strcpy((char*)temp, pi->name);

					if(!(strcmp((char*)temp,(char*)temp2)) || !(strcmp((char*)temp,"All-Spell Scroll")))
					{
						sysmessage(s,"You already have that spell!");
						item_bounce6(ps,pItem);
						return;
					}
				}
			}
		}
	}
	
	// player run vendors
	if (!(pCont->pileable && pItem->pileable && pCont->id()==pItem->id()
		|| (pCont->type!=1 && pCont->type!=9)))
	{
		j=DEREF_P_CHAR(GetPackOwner(pCont));
		if (j>-1) // bugkilling, LB, was j=!-1, arghh, C !!!
		{
			if (chars[j].npcaitype==17 && chars[j].isNpc() && pc_currchar->Owns(&chars[j]))
			{
				pc_currchar->inputitem = pItem->serial;
				pc_currchar->inputmode = cChar::enPricing;
				sysmessage(s, "Set a price for this item.");
			}
		}

		short xx=pp->TxLoc;
		short yy=pp->TyLoc;

		pCont->AddItem(pItem,xx,yy);
		
		itemsfx(s, pItem->id());// see itemsfx() for details - Dupois Added Oct 09, 1998
		statwindow(s,DEREF_P_CHAR(pc_currchar));
	}
	// end of player run vendors
	
	else
		// - Unlocked item spawner or unlockable item spawner
		if (pCont->type==63 || pCont->type==65 || pCont->type==66)
		{
			pItem->SetContSerial(pp->Tserial);

			// lb bugfix
			pItem->pos.x=pp->TxLoc;
			pItem->pos.y=pp->TyLoc;
			pItem->pos.z=pp->TzLoc;
			
			SndRemoveitem(pItem->serial);
			RefreshItem(pItem);//AntiChrist
			itemsfx(s, pItem->id());
			
		}
		else  // - Pileable
			if (pCont->pileable && pItem->pileable && pCont->id()==pItem->id())
			{		
				if ((pCont->amount+pItem->amount) > 65535)
				{
					pItem->amount -= (65535-pCont->amount);
					Commands->DupeItem(s, pCont, pItem->amount);
					pCont->amount = 65535;
					Items->DeleItem(pItem);
				}
				else
				{
					pCont->amount=pCont->amount+pItem->amount;
					itemsfx(s, pItem->id());
					Items->DeleItem(pItem);
				}
				SndRemoveitem(pItem->serial);
				RefreshItem(pCont);//AntiChrist
			}
			else
			{
				pItem->pos.x=pp->TxLoc;
				pItem->pos.y=pp->TyLoc;
				pItem->pos.z=pp->TzLoc;
//				pItem->SetContSerial(-1);
				pItem->SetContSerial(pp->Tserial);
				// Tauriel add item to world mapcells
				mapRegions->Add(pItem); //add this item to a map cell
				
				SndRemoveitem(pItem->serial);
				RefreshItem(pCont);//AntiChrist
			}
			
			// - Spell Book
	
			if (pCont->type==9)
				Magic->SpellBook(s, pCont); // LB, bugfix for showing(!) the wrong spell (clumsy) when a new spell is put into opened spellbook

			if (pItem->glow>0) // LB's glowing items stuff
			{
				int p = DEREF_P_CHAR(GetPackOwner(pCont)); 
				pc_currchar->removeHalo(pItem); // if gm put glowing object in another pack, handle glowsp correctly !
				if (p!=-1) 
				{
					chars[p].addHalo(pItem);
					chars[p].glowHalo(pItem);
				}		   
				
			}	
}
void get_item(P_CLIENT ps) // Client grabs an item
{
	int x,  npc=-1, c, amount, update = 0, serial;
//	tile_st tile;
	int z;// antichrist for trade fix
	UOXSOCKET s = ps->GetSocket();
	int cc = ps->GetCurrChar();
	P_CHAR pc_currchar = MAKE_CHARREF_LR(cc);
	
	
	serial = calcserial(buffer[s][1], buffer[s][2], buffer[s][3], buffer[s][4]);
	if (serial == INVALID_SERIAL || buffer[s][1] < 0x40)
		return;	// landscape or a character
	P_ITEM pi = FindItemBySerial(serial);
	if (pi == NULL)
		return;
	
	pc_currchar->disturbMed(s); // Meditation
	
	// Zippy's stealing changes  
	x = DEREF_P_ITEM(pi);
	if (!items[x].isInWorld())  // Find character owning item
	{
		int loopexit = 0;
		do  // Find character owning item
		{
			if (isCharSerial(items[x].contserial))
			{
				npc = calcCharFromSer(items[x].contserial);
			}
			else  // its an item
			{
				if (items[x].isInWorld())
				{
					npc=-1;
					break;
				}
				x = calcItemFromSer(items[x].contserial);
				// ANTICHRIST -- SECURE TRADE FIX
				if (x!=-1) // LB overwriting x is essential here, dont change it!!!
				{
					if (items[x].layer == 0 && items[x].id() == 0x1E5E)
					{
						// Trade window???
						serial = calcserial(items[x].moreb1, items[x].moreb2, items[x].moreb3, items[x].moreb4);
						if (serial == INVALID_SERIAL)
							return;
						z = calcItemFromSer(serial);
						if (z!=-1)
							if ((items[z].morez || items[x].morez))
							{
								items[z].morez = 0;
								items[x].morez = 0;
								sendtradestatus(z, x);
							}
					}
					// Blackwinds Looting is crime implementation
					// changed slightly by Ripper
					if (items[x].corpse != 0 && !pc_currchar->Owns(&items[x])) 
					{ 
						P_CHAR co = FindCharBySerial(items[x].ownserial);
						if (items[x].more2 == 1 && Guilds->Compare(cc, DEREF_P_CHAR(co)) == 0) 
						{ 
							pc_currchar->karma -= 5; 
							criminal(cc);
							sysmessage(s, "You lost some karma!"); 
						} 
						npc = 0;
					} // Criminal stuff
					if (items[x].corpse != 0)
						npc = 0;
				} // end if x!=-1
				
				if (x==-1)
					npc = 0; 
			}
		} while ((npc==-1) &&(++loopexit < MAXLOOPS));
	}
	
	if (npc>0) // 0=corpse, hence >0 ..
	{
		if (!(pc_currchar->isGM()) && npc != cc && ! pc_currchar->Owns(&chars[npc]))
		{// Own serial stuff by Zippy -^ Pack aniamls and vendors.
			bounce[1] = 0;
			Xsend(s, bounce, 2);
			if (ps->IsDragging())
			{
				ps->ResetDragging();
				item_bounce3(pi);
				pi->magic = 3;
			} 
			return;
		}
	}
	// End Zippy's change
	
	// Boats->
	if (x!=-1 && npc!=-1)
	{
		if (items[x].multis>0)
			imultisp.remove(items[x].multis, items[x].serial);
		items[x].startDecay();
		// End Boats Change
		
		// AntiChrist -- for poisoned items
		if (items[x].layer>0)
		{
			chars[npc].removeItemBonus(&items[x]);	// remove BONUS STATS given by equipped special items
		}
		if ((items[x].trigon==1) && (items[x].layer != 0) && (items[x].layer != 15) && (items[x].layer < 19))// -Frazurbluu- Trigger Type 2 is my new trigger type *-
		{
			triggerwitem(s, DEREF_P_ITEM(pi), 1); // trigger is fired
		}	
			// AntiChrist -- for poisoned items
		if (items[x].poisoned)
		{
			chars[npc].poison -= items[x].poisoned;
			if (chars[npc].poison < 0)
				chars[npc].poison = 0;
		}
	}
	if (pi != NULL)
	{
		if (pi->corpse != 1)
		{
			UpdateStatusWindow(s, pi);
			if (!pc_currchar->canPickUp(pi))
			{
				bounce[1] = 0;
				Xsend(s, bounce, 2);
				if (ps->IsDragging()) // only restore item if it got draggged before !!!
				{
					ps->ResetDragging();
					item_bounce4(s, pi);
				}
			}
			else
			{
				// AntiChrist bugfix for the bad bouncing bug ( disappearing items when bouncing )
				DRAGGED[s] = 1;
				
				pi->oldx = pi->pos.x;	// first let's save the position
				pi->oldy = pi->pos.y;
				pi->oldz = pi->pos.z;
				pi->oldcontserial = pi->contserial;	// then let's save the container
				pi->oldlayer = pi->layer;	// then the layer
				
				pi->layer = 0;
				if (!pi->isInWorld())
					soundeffect(s, 0x00, 0x57);
				if (pi->amount>1)
				{
					amount = (buffer[s][5] << 8) + buffer[s][6];
					if (amount>pi->amount)
						amount = pi->amount;
					if (amount < pi->amount)
					{
						c=Items->MemItemFree();
						items[c].Init(0);
						memcpy(&items[c], pi, sizeof(cItem));  // Tauriel reduce code faster too
						items[c].SetSerial(itemcount2);
						itemcount2++;

						items[c].amount = pi->amount - amount;
						// Tauriel sorry, there is no way to make this call the item creation stuff
// Why doing it twice?
//						setptr(&itemsp[itemcount2%HASHMAX], c);
//						itemcount2++; // important bugfix for items disappearing, lb
						if (!items[c].isInWorld())
							contsp.insert(items[c].contserial, items[c].serial);
						if (items[c].ownserial!=-1)
							setptr(&ownsp[items[c].ownserial%HASHMAX], c);
						if (items[c].spawnserial!=-1)
							setptr(&spawnsp[items[c].spawnserial%HASHMAX], c);
						
						statwindow(s,cc);
						RefreshItem(c);//AntiChrist
					}
					
					if (pi->id() == 0x0EED) // gold coin
					{
						int packnum = packitem(currchar[s]);
						if (packnum!=-1) // lb
							if (pi->contserial == items[packnum].serial)
								update = 1;
					}
					
					pi->amount = amount;
				}
				
				// Tauriel remove item from world mapcells
				mapRegions->Remove(pi); // remove this item from a map cell
				pi->pos.x = 0;
				pi->pos.y = 0;
				pi->pos.z = 0;
				
				pi->flags.isBeeingDragged=true;
				pi->SetContSerial(-1);
				if (pi != NULL) // Ripper...adds weight to the players cursor when carrying a item.
				{
					int amt = 0, wgt;
					wgt = (int)Weight->LockeddownWeight(pi, &amt, 0);
					pc_currchar->weight += wgt;
					update = 1;
				}
			}
		}
	} // end of if i!=-1
	if (update)
		statwindow(s, DEREF_P_CHAR(pc_currchar));
}