فهرست منبع

* Fixed bug 101, placing artifacts in specific slots in the backpack. Cleaned up swapArtifacts() to use more descriptive names as well.

OnionKnight 16 سال پیش
والد
کامیت
64a72c39cb
4فایلهای تغییر یافته به همراه57 افزوده شده و 36 حذف شده
  1. 8 8
      client/GUIClasses.cpp
  2. 6 5
      lib/NetPacksLib.cpp
  3. 42 22
      server/CGameHandler.cpp
  4. 1 1
      server/CGameHandler.h

+ 8 - 8
client/GUIClasses.cpp

@@ -3523,8 +3523,8 @@ void CArtPlace::clickLeft(tribool down, bool previousState)
 		}
 		else //perform artifact substitution
 		{
-			if(slotID >= 19)	//we are an backpack slot - remove active artifact and put it to the last free pos in backpack
-			{					//TODO: putting artifacts in the middle of backpack (pushing following arts)
+			if (slotID >= 19) // Backpack slot - Remove active artifact and insert it into the designated position in backpack.
+			{
 				const CArtifact *cur = ourOwner->commonInfo->activeArtPlace->ourArt;
 				assert(cur); //there is highlighted slot, it must contain an art
 				switch(cur->id)
@@ -3544,21 +3544,21 @@ void CArtPlace::clickLeft(tribool down, bool previousState)
 						ourOwner->commonInfo->activeArtPlace->ourOwner->curHero,
 						ourOwner->commonInfo->activeArtPlace->slotID,
 						ourOwner->curHero,
-						ourOwner->curHero->artifacts.size() + 19);
+						slotID);
 					break;
 				}
 			}
 			//check if swap is possible
 			else if(this->fitsHere(ourOwner->commonInfo->activeArtPlace->ourArt) && ourOwner->commonInfo->activeArtPlace->fitsHere(this->ourArt))
 			{
-				int destSlot = slotID,
-					srcSlot = ourOwner->commonInfo->activeArtPlace->slotID;
+				int srcSlot = ourOwner->commonInfo->activeArtPlace->slotID;
+				int destSlot = slotID;
 
 				LOCPLINT->cb->swapArtifacts(
-					ourOwner->curHero,
-					destSlot,
 					ourOwner->commonInfo->activeArtPlace->ourOwner->curHero,
-					srcSlot);
+					srcSlot,
+					ourOwner->curHero,
+					destSlot);
 
 				ourOwner->commonInfo->activeArtPlace->clicked = false;
 				ourOwner->commonInfo->activeArtPlace = NULL;

+ 6 - 5
lib/NetPacksLib.cpp

@@ -451,17 +451,18 @@ DLL_EXPORT void SetHeroArtifacts::setArtAtPos(ui16 pos, int art)
 		if(pos<19)
 			artifWorn.erase(pos);
 		else
-			artifacts -= artifacts[pos-19];
+			artifacts.erase(artifacts.begin() + (pos - 19));
 	}
 	else
 	{
-		if(pos<19)
+		if (pos < 19) {
 			artifWorn[pos] = art;
-		else
-			if(pos-19 < artifacts.size())
-				artifacts[pos-19] = art;
+		} else { // Goes into the backpack.
+			if(pos - 19 < artifacts.size())
+				artifacts.insert(artifacts.begin() + (pos - 19), art);
 			else
 				artifacts.push_back(art);
+		}
 	}
 }
 

+ 42 - 22
server/CGameHandler.cpp

@@ -2298,38 +2298,58 @@ bool CGameHandler::garrisonSwap( si32 tid )
 	}
 }
 
-bool CGameHandler::swapArtifacts( si32 hid1, si32 hid2, ui16 slot1, ui16 slot2 )
+bool CGameHandler::swapArtifacts(si32 srcHeroID, si32 destHeroID, ui16 srcSlot, ui16 destSlot)
 {
-	CGHeroInstance *h1 = gs->getHero(hid1), *h2 = gs->getHero(hid2);
-	if((distance(h1->pos,h2->pos) > 1.5)   ||   (h1->tempOwner != h2->tempOwner))
+	CGHeroInstance *srcHero = gs->getHero(srcHeroID);
+	CGHeroInstance *destHero = gs->getHero(destHeroID);
+
+	// Make sure exchange is even possible between the two heroes.
+	if ((distance(srcHero->pos,destHero->pos) > 1.5 )|| (srcHero->tempOwner != destHero->tempOwner))
 		return false;
 
-	const CArtifact *a1 = h1->getArt(slot1), 
-		*a2=h2->getArt(slot2);
+	const CArtifact *srcArtifact = srcHero->getArt(srcSlot); 
+	const CArtifact *destArtifact = destHero->getArt(destSlot);
 
-	//check if 
-	//	1) slots are appropriate for that artifacts 
-	//	2) they are not war machine
-	if((a1 && slot2<19 && !vstd::contains(a1->possibleSlots,slot2) || (a2 && slot1<19 && !vstd::contains(a2->possibleSlots,slot1))) && complain("Cannot swap artifacts!")
-		|| (slot1>=13 && slot1<=16 || slot2>=13 && slot2<=16) && complain("Cannot move war machine!")
-	)
+	// Check if src/dest slots are appropriate for the artifacts exchanged.
+	// Moving to the backpack is always allowed.
+	if ((!srcArtifact || destSlot < 19)
+		&& (((srcArtifact && !vstd::contains(srcArtifact->possibleSlots, destSlot))
+			|| (destArtifact && srcSlot < 19 && !vstd::contains(destArtifact->possibleSlots, srcSlot)))))
 	{
+		complain("Cannot swap artifacts!");
+		return false;
+	}
+
+	// Make sure the artifacts are not war machines.
+	if ((srcSlot>=13 && srcSlot<=16) || (destSlot>=13 && destSlot<=16)) {
+		complain("Cannot move war machine!");
 		return false;
 	}
 
+	// Perform the exchange.
 	SetHeroArtifacts sha;
-	sha.hid = hid1;
-	sha.artifacts = h1->artifacts;
-	sha.artifWorn = h1->artifWorn;
-	sha.setArtAtPos(slot1,h2->getArtAtPos(slot2));
-	if(h1 == h2) sha.setArtAtPos(slot2,h1->getArtAtPos(slot1));
+	sha.hid = srcHeroID;
+	sha.artifacts = srcHero->artifacts;
+	sha.artifWorn = srcHero->artifWorn;
+
+	sha.setArtAtPos(srcSlot, -1);
+	if (destSlot < 19 && (destArtifact || srcSlot < 19))
+		sha.setArtAtPos(srcSlot, destHero->getArtAtPos(destSlot));
+
+	// Correction for destination from removing source artifact in backpack.
+	if (srcSlot >= 19 && destSlot >= 19 && srcSlot < destSlot)
+		destSlot--;
+
+	// Internal hero artifact arrangement.
+	if(srcHero == destHero)
+		sha.setArtAtPos(destSlot, srcHero->getArtAtPos(srcSlot));
 	sendAndApply(&sha);
-	if(hid1 != hid2)
-	{
-		sha.hid = hid2;
-		sha.artifacts = h2->artifacts;
-		sha.artifWorn = h2->artifWorn;
-		sha.setArtAtPos(slot2, a1 ? a1->id : -1);
+	if (srcHeroID != destHeroID) {
+		// Exchange between two different heroes.
+		sha.hid = destHeroID;
+		sha.artifacts = destHero->artifacts;
+		sha.artifWorn = destHero->artifWorn;
+		sha.setArtAtPos(destSlot, srcArtifact ? srcArtifact->id : -1);
 		sendAndApply(&sha);
 	}
 

+ 1 - 1
server/CGameHandler.h

@@ -154,7 +154,7 @@ public:
 	bool setFormation( si32 hid, ui8 formation );
 	bool tradeResources( ui32 val, ui8 player, ui32 id1, ui32 id2 );
 	bool buyArtifact( ui32 hid, si32 aid );
-	bool swapArtifacts( si32 hid1, si32 hid2, ui16 slot1, ui16 slot2 );
+	bool swapArtifacts(si32 srcHeroID, si32 destHeroID, ui16 srcSlot, ui16 destSlot);
 	bool garrisonSwap(si32 tid);
 	bool upgradeCreature( ui32 objid, ui8 pos, ui32 upgID );
 	bool recruitCreatures(si32 objid, ui32 crid, ui32 cram);