예제 #1
0
/**
** Cast polymorph.
**
**  @param caster       Unit that casts the spell
**  @param spell        Spell-type pointer
**  @param target       Target unit that spell is addressed to
**  @param goalPos      coord of target spot when/if target does not exist
**
**  @return             =!0 if spell should be repeated, 0 if not
*/
/* virtual */ int Spell_Polymorph::Cast(CUnit &caster, const SpellType &spell, CUnit *target, const Vec2i &goalPos)
{
	if (!target) {
		return 0;
	}
	CUnitType &type = *this->NewForm;
	const Vec2i pos(goalPos - type.GetHalfTileSize());

	caster.Player->Score += target->Variable[POINTS_INDEX].Value;
	if (caster.IsEnemy(*target)) {
		if (target->Type->Building) {
			caster.Player->TotalRazings++;
		} else {
			caster.Player->TotalKills++;
		}
		if (UseHPForXp) {
			caster.Variable[XP_INDEX].Max += target->Variable[HP_INDEX].Value;
		} else {
			caster.Variable[XP_INDEX].Max += target->Variable[POINTS_INDEX].Value;
		}
		caster.Variable[XP_INDEX].Value = caster.Variable[XP_INDEX].Max;
		caster.Variable[KILL_INDEX].Value++;
		caster.Variable[KILL_INDEX].Max++;
		caster.Variable[KILL_INDEX].Enable = 1;
	}

	// as said somewhere else -- no corpses :)
	target->Remove(NULL);
	Vec2i offset;
	for (offset.x = 0; offset.x < type.TileWidth; ++offset.x) {
		for (offset.y = 0; offset.y < type.TileHeight; ++offset.y) {
			if (!UnitTypeCanBeAt(type, pos + offset)) {
				target->Place(target->tilePos);
				return 0;
			}
		}
	}
	caster.Variable[MANA_INDEX].Value -= spell.ManaCost;
	if (this->PlayerNeutral == 1) {
		MakeUnitAndPlace(pos, type, Players + PlayerNumNeutral);
	} else if (this->PlayerNeutral == 2) {
		MakeUnitAndPlace(pos, type, caster.Player);
	} else {
		MakeUnitAndPlace(pos, type, target->Player);
	}
	UnitLost(*target);
	UnitClearOrders(*target);
	target->Release();
	return 1;
}
예제 #2
0
/**
** Cast circle of power.
**
**  @param caster       Unit that casts the spell
**  @param spell        Spell-type pointer
**  @param target       Target unit that spell is addressed to
**  @param goalPos      tilePos of target spot when/if target does not exist
**
**  @return             =!0 if spell should be repeated, 0 if not
*/
/* virtual */ int Spell_SpawnPortal::Cast(CUnit &caster, const SpellType &, CUnit *, const Vec2i &goalPos)
{
	// FIXME: vladi: cop should be placed only on explored land
	CUnit *portal = caster.Goal;

	DebugPrint("Spawning a portal exit.\n");
	if (portal) {
		portal->MoveToXY(goalPos);
	} else {
		portal = MakeUnitAndPlace(goalPos, *this->PortalType, &Players[PlayerNumNeutral]);
	}
	//  Goal is used to link to destination circle of power
	caster.Goal = portal;
	//FIXME: setting destination circle of power should use mana
	return 0;
}
예제 #3
0
/**
**  Game main loop.
**
**  Unit actions.
**  Missile actions.
**  Players (AI).
**  Cyclic events (color cycle,...)
**  Display update.
**  Input/Network/Sound.
*/
void GameMainLoop()
{
	const EventCallback *old_callbacks;

	InitGameCallbacks();

	old_callbacks = GetCallbacks();
	SetCallbacks(&GameCallbacks);

	SetVideoSync();
	GameCursor = UI.Point.Cursor;
	GameRunning = true;

	CParticleManager::init();

#ifdef REALVIDEO
	RealVideoSyncSpeed = VideoSyncSpeed;
#endif

	CclCommand("if (GameStarting ~= nil) then GameStarting() end");

	MultiPlayerReplayEachCycle();
	
	//Wyrmgus start
	//if the person player has no faction, bring up the faction choice interface
	if (!GrandStrategy && ThisPlayer && ThisPlayer->Faction == -1) {
		char buf[256];
		snprintf(buf, sizeof(buf), "if (ChooseFaction ~= nil) then ChooseFaction(\"%s\", \"%s\") end", ThisPlayer->Race != -1 ? PlayerRaces.Name[ThisPlayer->Race].c_str() : "", "");
		CclCommand(buf);
	}
	
	if (!IsNetworkGame() && ThisPlayer && CurrentCustomHero != NULL) {
		Vec2i resPos;
		FindNearestDrop(*CurrentCustomHero->Type, ThisPlayer->StartPos, resPos, LookingW);
		CUnit *custom_hero = MakeUnitAndPlace(resPos, *CurrentCustomHero->Type, ThisPlayer);
		custom_hero->SetCharacter(CurrentCustomHero->GetFullName(), true);	
	}
	//Wyrmgus end

	SingleGameLoop();

	//
	// Game over
	//
	if (GameResult == GameExit) {
		Exit(0);
		return;
	}

#ifdef REALVIDEO
	if (FastForwardCycle > GameCycle) {
		VideoSyncSpeed = RealVideoSyncSpeed;
	}
#endif
	NetworkQuitGame();
	EndReplayLog();

	GameCycle = 0;//????
	//Wyrmgus start
	GameTimeOfDay = NoTimeOfDay;
	//Wyrmgus end
	CParticleManager::exit();
	FlagRevealMap = 0;
	ReplayRevealMap = 0;
	GamePaused = false;
	GodMode = false;

	SetCallbacks(old_callbacks);
}
예제 #4
0
/**
**  Game main loop.
**
**  Unit actions.
**  Missile actions.
**  Players (AI).
**  Cyclic events (color cycle,...)
**  Display update.
**  Input/Network/Sound.
*/
void GameMainLoop()
{
	const EventCallback *old_callbacks;

	InitGameCallbacks();

	old_callbacks = GetCallbacks();
	SetCallbacks(&GameCallbacks);

	SetVideoSync();
	GameCursor = UI.Point.Cursor;
	//Wyrmgus start
	GameEstablishing = false;
	//Wyrmgus end
	GameRunning = true;

	CParticleManager::init();

#ifdef REALVIDEO
	RealVideoSyncSpeed = VideoSyncSpeed;
#endif

	CclCommand("if (GameStarting ~= nil) then GameStarting() end");

	MultiPlayerReplayEachCycle();
	
	//Wyrmgus start
	if (GameCycle == 0) { // so that these don't trigger when loading a saved game
		if (CurrentCampaign != NULL) {
			for (int i = 0; i < NumPlayers; ++i) {
				if (Players[i].Type != PlayerNobody && Players[i].Race != 0 && Players[i].Faction != -1) {
					if (CurrentCampaign->StartDate.year) {
						CCivilization *civilization = PlayerRaces.Civilizations[Players[i].Race];
						CFaction *faction = PlayerRaces.Factions[Players[i].Race][Players[i].Faction];
						
						for (std::map<std::string, std::map<CDate, bool>>::iterator iterator = civilization->HistoricalUpgrades.begin(); iterator != civilization->HistoricalUpgrades.end(); ++iterator) {
							int upgrade_id = UpgradeIdByIdent(iterator->first);
							if (upgrade_id == -1) {
								fprintf(stderr, "Upgrade \"%s\" doesn't exist.\n", iterator->first.c_str());
								continue;
							}
							for (std::map<CDate, bool>::reverse_iterator second_iterator = iterator->second.rbegin(); second_iterator != iterator->second.rend(); ++second_iterator) {
								if (second_iterator->first.year == 0 || CurrentCampaign->StartDate >= second_iterator->first) {
									if (second_iterator->second && UpgradeIdentAllowed(Players[i], iterator->first.c_str()) != 'R') {
										UpgradeAcquire(Players[i], AllUpgrades[upgrade_id]);
									} else if (!second_iterator->second) {
										break;
									}
								}
							}
						}
						
						for (std::map<std::string, std::map<CDate, bool>>::iterator iterator = faction->HistoricalUpgrades.begin(); iterator != faction->HistoricalUpgrades.end(); ++iterator) {
							int upgrade_id = UpgradeIdByIdent(iterator->first);
							if (upgrade_id == -1) {
								fprintf(stderr, "Upgrade \"%s\" doesn't exist.\n", iterator->first.c_str());
								continue;
							}
							for (std::map<CDate, bool>::reverse_iterator second_iterator = iterator->second.rbegin(); second_iterator != iterator->second.rend(); ++second_iterator) {
								if (second_iterator->first.year == 0 || CurrentCampaign->StartDate >= second_iterator->first) {
									if (second_iterator->second && UpgradeIdentAllowed(Players[i], iterator->first.c_str()) != 'R') {
										UpgradeAcquire(Players[i], AllUpgrades[upgrade_id]);
									} else if (!second_iterator->second) {
										break;
									}
								}
							}
						}

						for (std::map<std::pair<int, CFaction *>, int>::iterator iterator = faction->HistoricalDiplomacyStates.begin(); iterator != faction->HistoricalDiplomacyStates.end(); ++iterator) { //set the appropriate historical diplomacy states to other factions
							if (iterator->second == 0 || CurrentCampaign->StartDate.year >= iterator->first.first) {
								CPlayer *diplomacy_state_player = GetFactionPlayer(iterator->first.second);
								if (diplomacy_state_player) {
									CommandDiplomacy(i, iterator->second, diplomacy_state_player->Index);
									CommandDiplomacy(diplomacy_state_player->Index, iterator->second, i);
									if (iterator->second == DiplomacyAllied) {
										CommandSharedVision(i, true, diplomacy_state_player->Index);
										CommandSharedVision(diplomacy_state_player->Index, true, i);
									}
								}
							}
						}

						for (std::map<std::pair<CDate, int>, int>::iterator iterator = faction->HistoricalResources.begin(); iterator != faction->HistoricalResources.end(); ++iterator) { //set the appropriate historical resource quantities
							if (iterator->second == 0 || CurrentCampaign->StartDate >= iterator->first.first) {
								Players[i].SetResource(iterator->first.second, iterator->second);
							}
						}
					}
				}
			}
	
			if (CurrentCampaign->StartEffects) {
				CurrentCampaign->StartEffects->pushPreamble();
				CurrentCampaign->StartEffects->run();
			}
		}
		
		//if the person player has no faction, bring up the faction choice interface
		if (!GrandStrategy && ThisPlayer && ThisPlayer->Faction == -1) {
			char buf[256];
			snprintf(buf, sizeof(buf), "if (ChooseFaction ~= nil) then ChooseFaction(\"%s\", \"%s\") end", ThisPlayer->Race != -1 ? PlayerRaces.Name[ThisPlayer->Race].c_str() : "", "");
			CclCommand(buf);
		}
		
		if (!IsNetworkGame() && ThisPlayer && CurrentCustomHero != NULL) {
			Vec2i resPos;
			FindNearestDrop(*CurrentCustomHero->Type, ThisPlayer->StartPos, resPos, LookingW, ThisPlayer->StartMapLayer);
			CUnit *custom_hero = MakeUnitAndPlace(resPos, *CurrentCustomHero->Type, ThisPlayer, ThisPlayer->StartMapLayer);
			custom_hero->SetCharacter(CurrentCustomHero->Ident, true);	
		}
		
		if (CurrentQuest != NULL && CurrentQuest->IntroductionDialogue != NULL) {
			CurrentQuest->IntroductionDialogue->Call(ThisPlayer->Index);
		}
	}
	//Wyrmgus end

	SingleGameLoop();

	//
	// Game over
	//
	if (GameResult == GameExit) {
		Exit(0);
		return;
	}

#ifdef REALVIDEO
	if (FastForwardCycle > GameCycle) {
		VideoSyncSpeed = RealVideoSyncSpeed;
	}
#endif
	NetworkQuitGame();
	EndReplayLog();

	GameCycle = 0;//????
	CParticleManager::exit();
	FlagRevealMap = 0;
	ReplayRevealMap = 0;
	GamePaused = false;
	GodMode = false;

	SetCallbacks(old_callbacks);
}
예제 #5
0
파일: edmap.cpp 프로젝트: akien-mga/Wyrmgus
/**
**  Add a unit to random locations on the map, unit will be neutral
**
**  @param unit_type  unit type to add to map as a character string
**  @param count      the number of times to add the unit
**  @param value      resources to be stored in that unit
*/
static void EditorRandomizeUnit(const char *unit_type, int count, int value)
{
	//Wyrmgus start
//	const Vec2i mpos(Map.Info.MapWidth, Map.Info.MapHeight);
	const Vec2i mpos(Map.Info.MapWidths[CurrentMapLayer], Map.Info.MapHeights[CurrentMapLayer]);
	//Wyrmgus end
	CUnitType *typeptr = UnitTypeByIdent(unit_type);

	if (!typeptr) { // Error
		return;
	}
	CUnitType &type = *typeptr;
	const Vec2i tpos(type.TileWidth, type.TileHeight);

	for (int i = 0; i < count; ++i) {
		const Vec2i rpos(rand() % (mpos.x / 2 - tpos.x + 1), rand() % (mpos.y / 2 - tpos.y + 1));
		const Vec2i mirror(mpos.x - rpos.x - 1, mpos.y - rpos.y - 1);
		const Vec2i mirrorh(rpos.x, mirror.y);
		const Vec2i mirrorv(mirror.x, rpos.y);
		const Vec2i tmirror(mpos.x - rpos.x - tpos.x, mpos.y - rpos.y - tpos.y);
		const Vec2i tmirrorh(rpos.x, tmirror.y);
		const Vec2i tmirrorv(tmirror.x, rpos.y);
		int tile = GRASS_TILE;
		const int z = type.TileHeight;

		// FIXME: vladi: the idea is simple: make proper land for unit(s) :)
		// FIXME: handle units larger than 1 square
		TileFill(rpos, tile, z * 2);
		TileFill(mirrorh, tile, z * 2);
		TileFill(mirrorv, tile, z * 2);
		TileFill(mirror, tile, z * 2);

		// FIXME: can overlap units
		//Wyrmgus start
//		CUnit *unit = MakeUnitAndPlace(rpos, type, &Players[PlayerNumNeutral]);
		CUnit *unit = MakeUnitAndPlace(rpos, type, &Players[PlayerNumNeutral], CurrentMapLayer);
		//Wyrmgus end
		if (unit == NULL) {
			DebugPrint("Unable to allocate Unit");
		} else {
			//Wyrmgus start
//			unit->ResourcesHeld = value;
			unit->SetResourcesHeld(value);
			//Wyrmgus end
		}

		//Wyrmgus start
//		unit = MakeUnitAndPlace(tmirrorh, type, &Players[PlayerNumNeutral]);
		unit = MakeUnitAndPlace(tmirrorh, type, &Players[PlayerNumNeutral], CurrentMapLayer);
		//Wyrmgus end
		if (unit == NULL) {
			DebugPrint("Unable to allocate Unit");
		} else {
			//Wyrmgus start
//			unit->ResourcesHeld = value;
			unit->SetResourcesHeld(value);
			//Wyrmgus end
		}

		//Wyrmgus start
//		unit = MakeUnitAndPlace(tmirrorv, type, &Players[PlayerNumNeutral]);
		unit = MakeUnitAndPlace(tmirrorv, type, &Players[PlayerNumNeutral], CurrentMapLayer);
		//Wyrmgus end
		if (unit == NULL) {
			DebugPrint("Unable to allocate Unit");
		} else {
			//Wyrmgus start
//			unit->ResourcesHeld = value;
			unit->SetResourcesHeld(value);
			//Wyrmgus end
		}

		//Wyrmgus start
//		unit = MakeUnitAndPlace(tmirror, type, &Players[PlayerNumNeutral]);
		unit = MakeUnitAndPlace(tmirror, type, &Players[PlayerNumNeutral], CurrentMapLayer);
		//Wyrmgus end
		if (unit == NULL) {
			DebugPrint("Unable to allocate Unit");
		} else {
			//Wyrmgus start
//			unit->ResourcesHeld = value;
			unit->SetResourcesHeld(value);
			//Wyrmgus end
		}
	}
}