void GenerateSnapshot (CUniverse &Universe, CXMLElement *pCmdLine) { ALERROR error; int i; // Get some parameters int iInitialUpdateTime = 10; int iUpdateTime = pCmdLine->GetAttributeInteger(CONSTLIT("wait")); // Criteria CString sNode = pCmdLine->GetAttribute(CONSTLIT("node")); CString sCriteria = pCmdLine->GetAttribute(CONSTLIT("criteria")); // Output int cxWidth; int cyHeight; if (pCmdLine->FindAttributeInteger(CONSTLIT("size"), &cxWidth)) { cyHeight = cxWidth; } else { cxWidth = 1024; cyHeight = 1024; } // Paint flags DWORD dwPaintFlags = 0; if (pCmdLine->GetAttributeBool(CONSTLIT("noStars"))) dwPaintFlags |= CSystem::VWP_NO_STAR_FIELD; // Output file CString sFilespec = pCmdLine->GetAttribute(CONSTLIT("output")); if (!sFilespec.IsBlank()) sFilespec = pathAddExtensionIfNecessary(sFilespec, CONSTLIT(".bmp")); // Update context SSystemUpdateCtx Ctx; Ctx.bForceEventFiring = true; Ctx.bForcePainted = true; // Loop over all systems until we find what we're looking for int iLoops = 20; int iNodeIndex = 0; CTopologyNode *pNode = Universe.GetTopologyNode(iNodeIndex); while (true) { // Create the system CSystem *pSystem; if (error = Universe.CreateStarSystem(pNode, &pSystem)) { printf("ERROR: Unable to create star system.\n"); return; } // If this is the node we want, then search CSpaceObject *pTarget; if (sNode.IsBlank() || strEquals(sNode, pNode->GetID())) { printf("Searching %s...\n", pNode->GetSystemName().GetASCIIZPointer()); // Set the POV CSpaceObject *pPOV = pSystem->GetObject(0); Universe.SetPOV(pPOV); pSystem->SetPOVLRS(pPOV); // Prepare system Universe.UpdateExtended(); Universe.GarbageCollectLibraryBitmaps(); // Update for a while for (i = 0; i < iInitialUpdateTime; i++) Universe.Update(Ctx); // Compose the criteria CSpaceObject::Criteria Criteria; CSpaceObject::ParseCriteria(pPOV, sCriteria, &Criteria); // Get the list of all objects in the system that match the criteria CSpaceObject::SCriteriaMatchCtx Ctx(Criteria); TArray<CSpaceObject *> Results; for (i = 0; i < pSystem->GetObjectCount(); i++) { CSpaceObject *pObj = pSystem->GetObject(i); if (pObj && pObj->MatchesCriteria(Ctx, Criteria)) Results.Insert(pObj); } // Pick the appropriate object from the list if (Results.GetCount() == 0) pTarget = NULL; else if (Criteria.bNearestOnly || Criteria.bFarthestOnly) pTarget = Ctx.pBestObj; else pTarget = Results[mathRandom(0, Results.GetCount() - 1)]; } else pTarget = NULL; // If we found the target, then output if (pTarget) { // If we found the target, take a snapshot printf("Found %s.\n", pTarget->GetNounPhrase(0).GetASCIIZPointer()); // Wait a bit for (i = 0; i < iUpdateTime; i++) { if ((i % 100) == 99) printf("."); Universe.Update(Ctx); } if (iUpdateTime >= 99) printf("\n"); // Paint CG16bitImage Output; Output.CreateBlank(cxWidth, cyHeight, false); RECT rcViewport; rcViewport.left = 0; rcViewport.top = 0; rcViewport.right = cxWidth; rcViewport.bottom = cyHeight; pSystem->PaintViewport(Output, rcViewport, pTarget, dwPaintFlags); // Write to file if (!sFilespec.IsBlank()) { CFileWriteStream OutputFile(sFilespec); if (OutputFile.Create() != NOERROR) { printf("ERROR: Unable to create '%s'\n", sFilespec.GetASCIIZPointer()); return; } Output.WriteToWindowsBMP(&OutputFile); OutputFile.Close(); printf("%s\n", sFilespec.GetASCIIZPointer()); } // Otherwise, clipboard else { if (error = Output.CopyToClipboard()) { printf("ERROR: Unable to copy image to clipboard.\n"); return; } printf("Image copied to clipboard.\n"); } // Done break; } // Done with old system Universe.DestroySystem(pSystem); // Loop to the next node do { iNodeIndex = ((iNodeIndex + 1) % Universe.GetTopologyNodeCount()); pNode = Universe.GetTopologyNode(iNodeIndex); } while (pNode == NULL || pNode->IsEndGame()); // If we're back to the first node again, restart if (iNodeIndex == 0) { if (--iLoops > 0) { Universe.Reinit(); iNodeIndex = 0; pNode = Universe.GetTopologyNode(iNodeIndex); } else { printf("ERROR: Specified target could not be found.\n"); return; } } } }
EResults RunEncounter (CUniverse &Universe, CSimViewer &Viewer, CStationType *pDefenderType, CShipClass *pAttackerClass, CSovereign *pAttackerSovereign) { int iTimeOut = DEFAULT_TIME_OUT; // Make sure the universe is clean CString sError; if (Universe.InitGame(0, &sError) != NOERROR) { printf("ERROR: %s", sError.GetASCIIZPointer()); return resultError; } // Create an empty system CSystem *pSystem; if (Universe.CreateEmptyStarSystem(&pSystem) != NOERROR) { printf("ERROR: Unable to create empty star system.\n"); return resultError; } // Create a station in the center of the system CSpaceObject *pStation; if (pSystem->CreateStation(pDefenderType, NULL, CVector(), &pStation) != NOERROR) { printf("ERROR: Unable to create station.\n"); return resultError; } // Set the POV Universe.SetPOV(pStation); pSystem->SetPOVLRS(pStation); // Prepare system Universe.UpdateExtended(); Universe.GarbageCollectLibraryBitmaps(); Universe.StartGame(true); // Now create an attacker some distance away CVector vPos = PolarToVector(mathRandom(0, 359), INITIAL_DISTANCE); CShip *pAttacker; if (pSystem->CreateShip(pAttackerClass->GetUNID(), NULL, NULL, pAttackerSovereign, vPos, CVector(), 0, NULL, NULL, &pAttacker) != NOERROR) { printf("ERROR: Unable to create attacking ship.\n"); return resultError; } // Set the attacker to attack the station IShipController *pController = pAttacker->GetController(); if (pController == NULL) { printf("ERROR: No controller for ship.\n"); return resultError; } pController->AddOrder(IShipController::orderAttackStation, pStation, IShipController::SData()); // Watch the attacker Universe.SetPOV(pAttacker); pSystem->SetPOVLRS(pAttacker); // Update context SSystemUpdateCtx Ctx; Ctx.bForceEventFiring = true; Ctx.bForcePainted = true; // Now keep updating until either the station is destroyed, the ship is destroyed, or we time-out int iTime = 0; int iDestroyedTime = (Viewer.IsEmpty() ? 0 : DESTROY_TIME); bool bDestroyed = false; EResults iResult = resultTimeout; while (iTime < iTimeOut && (!bDestroyed || iDestroyedTime > 0)) { iTime++; Universe.Update(Ctx); if (!Viewer.IsEmpty()) Viewer.PaintViewport(Universe); if (bDestroyed) iDestroyedTime--; else if (pStation->IsDestroyed() || pStation->IsAbandoned()) { bDestroyed = true; iResult = resultDefenderDestroyed; } else if (pAttacker->IsDestroyed()) { bDestroyed = true; iResult = resultAttackerDestroyed; } } // Done return iResult; }
void TestUpdate (CUniverse &Universe, CXMLElement *pCmdLine) { int i; int iTrial; TArray<DWORD> Trials; DWORD dwLastAverage; // How many tests int iCount = pCmdLine->GetAttributeInteger(CONSTLIT("count")); if (iCount == 0) iCount = 1; // How long do we update int iUpdateCount = pCmdLine->GetAttributeInteger(CONSTLIT("updateCount")); if (iUpdateCount == 0) iUpdateCount = DEFAULT_UPDATE; // Create the fist system for (iTrial = 0; iTrial < iCount; iTrial++) { TArray<SSample> Timings; printf("Trial: %d\n", iTrial + 1); // Initialize the universe CString sError; if (Universe.InitGame(0, &sError) != NOERROR) { printf("ERROR: %s", sError.GetASCIIZPointer()); return; } // Create the first system CTopologyNode *pNode = Universe.GetFirstTopologyNode(); if (pNode == NULL) { printf("ERROR: Cannot find first node.\n"); return; } CSystem *pSystem; if (Universe.CreateStarSystem(pNode, &pSystem) != NOERROR) { printf("ERROR: Unable to create star system.\n"); return; } // Set the POV CSpaceObject *pPOV = pSystem->GetObject(0); Universe.SetPOV(pPOV); pSystem->SetPOVLRS(pPOV); // Prepare system Universe.UpdateExtended(); Universe.GarbageCollectLibraryBitmaps(); Universe.StartGame(true); // Update context SSystemUpdateCtx Ctx; Ctx.bForceEventFiring = true; Ctx.bForcePainted = true; // Update for a while DWORD dwStart = ::GetTickCount(); for (i = 0; i < iUpdateCount; i++) { Universe.Update(Ctx); if (i > 0 && (i % SAMPLE_SIZE) == 0) { DWORD dwEnd = ::GetTickCount(); DWORD dwTime = dwEnd - dwStart; SSample *pSample = Timings.Insert(); pSample->dwTime = dwTime; pSample->iObjCount = GetValidObjCount(pSystem); CString sTime = strFormatMilliseconds(dwTime); CString sObjTime = strFormatMicroseconds(1000 * dwTime / pSample->iObjCount); printf("Objs: %d Total time: %s Per obj: %s\n", pSample->iObjCount, sTime.GetASCIIZPointer(), sObjTime.GetASCIIZPointer()); dwStart = ::GetTickCount(); } } // Compute trial average DWORD dwTotal = 0; DWORD dwAverage = 0; for (i = 0; i < Timings.GetCount(); i++) dwTotal += Timings[i].dwTime; if (Timings.GetCount() > 0) { dwAverage = dwTotal / Timings.GetCount(); CString sTime = strFormatMilliseconds(dwAverage); printf("Trial average: %s\n", sTime.GetASCIIZPointer()); } Trials.Insert(dwAverage); // Compute total average dwTotal = 0; for (i = 0; i < Trials.GetCount(); i++) dwTotal += Trials[i]; dwLastAverage = dwTotal / Trials.GetCount(); CString sTime = strFormatMilliseconds(dwLastAverage); printf("\n"); printf("Running average: %s\n", sTime.GetASCIIZPointer()); printf("\n"); } // Final tally CString sTime = strFormatMilliseconds(dwLastAverage); CString sTime2 = strFormatMicroseconds(1000 * dwLastAverage / SAMPLE_SIZE); printf("Total updates: %d\n", iUpdateCount * iCount); printf("Average time for %d updates: %s\n", SAMPLE_SIZE, sTime.GetASCIIZPointer()); printf("Average time per update: %s\n", sTime2.GetASCIIZPointer()); }
void GenerateSnapshot (CUniverse &Universe, CXMLElement *pCmdLine) { ALERROR error; int i; // Get some parameters int iInitialUpdateTime = pCmdLine->GetAttributeIntegerBounded(CONSTLIT("initialUpdate"), 0, -1, 10); int iUpdateTime = pCmdLine->GetAttributeInteger(CONSTLIT("wait")); bool bObjOnly = pCmdLine->GetAttributeBool(CONSTLIT("objOnly")); // Criteria CString sNode = pCmdLine->GetAttribute(CONSTLIT("node")); CString sCriteria = pCmdLine->GetAttribute(CONSTLIT("criteria")); // Number of snapshots int iTotalCount = pCmdLine->GetAttributeIntegerBounded(CONSTLIT("count"), 1, -1, 1); // Output int cxWidth; int cyHeight; if (pCmdLine->FindAttributeInteger(CONSTLIT("size"), &cxWidth)) { cyHeight = cxWidth; } else { cxWidth = 1024; cyHeight = 1024; } // Paint flags DWORD dwPaintFlags = 0; if (pCmdLine->GetAttributeBool(CONSTLIT("noStars"))) dwPaintFlags |= CSystem::VWP_NO_STAR_FIELD; // Output file CString sFilespec = pCmdLine->GetAttribute(CONSTLIT("output")); if (!sFilespec.IsBlank()) sFilespec = pathStripExtension(sFilespec); // Output image CG32bitImage Output; Output.Create(cxWidth, cyHeight); // Update context SSystemUpdateCtx Ctx; Ctx.bForceEventFiring = true; Ctx.bForcePainted = true; RECT rcViewport; rcViewport.left = 0; rcViewport.top = 0; rcViewport.right = cxWidth; rcViewport.bottom = cyHeight; // Loop over all systems until we find what we're looking for int iLoops = 20; int iNodeIndex = 0; int iSnapshotIndex = 0; CTopologyNode *pNode = Universe.GetTopologyNode(iNodeIndex); while (true) { // Create the system CSystem *pSystem; if (error = Universe.CreateStarSystem(pNode, &pSystem)) { printf("ERROR: Unable to create star system.\n"); return; } // If this is the node we want, then search CSpaceObject *pTarget; if (sNode.IsBlank() || strEquals(sNode, pNode->GetID())) { printf("Searching %s...\n", pNode->GetSystemName().GetASCIIZPointer()); // Set the POV CSpaceObject *pPOV = pSystem->GetObject(0); Universe.SetPOV(pPOV); pSystem->SetPOVLRS(pPOV); // Prepare system Universe.UpdateExtended(); Universe.GarbageCollectLibraryBitmaps(); // Update for a while for (i = 0; i < iInitialUpdateTime; i++) { Universe.Update(Ctx); Universe.PaintPOV(Output, rcViewport, 0); } // Compose the criteria CSpaceObject::Criteria Criteria; CSpaceObject::ParseCriteria(pPOV, sCriteria, &Criteria); // Get the list of all objects in the system that match the criteria CSpaceObject::SCriteriaMatchCtx Ctx(Criteria); TArray<CSpaceObject *> Results; for (i = 0; i < pSystem->GetObjectCount(); i++) { CSpaceObject *pObj = pSystem->GetObject(i); if (pObj && pObj->MatchesCriteria(Ctx, Criteria)) Results.Insert(pObj); } // Pick the appropriate object from the list if (Results.GetCount() == 0) pTarget = NULL; else if (Criteria.bNearestOnly || Criteria.bFarthestOnly) pTarget = Ctx.pBestObj; else pTarget = Results[mathRandom(0, Results.GetCount() - 1)]; } else pTarget = NULL; // If we found the target, then output if (pTarget) { Universe.SetPOV(pTarget); // Wait a bit // // NOTE: After we update, pTarget could be invalid (i.e., destroyed) // so we can't use it again. CString sTargetName = pTarget->GetNounPhrase(0); for (i = 0; i < iUpdateTime; i++) { if ((i % 100) == 99) printf("."); Universe.Update(Ctx); Universe.PaintPOV(Output, rcViewport, 0); } if (iUpdateTime >= 99) printf("\n"); // Paint if (bObjOnly) { SViewportPaintCtx Ctx; Ctx.pObj = Universe.GetPOV(); Ctx.XForm = ViewportTransform(Universe.GetPOV()->GetPos(), g_KlicksPerPixel, cxWidth / 2, cyHeight / 2); Ctx.XFormRel = Ctx.XForm; Ctx.fNoRecon = true; Ctx.fNoDockedShips = true; Ctx.fNoSelection = true; Ctx.fNoStarfield = true; CSpaceObject *pPOV = pSystem->GetObject(0); CSpaceObject::Criteria Criteria; CSpaceObject::ParseCriteria(pPOV, sCriteria, &Criteria); // Paint all objects that match the criteria CSpaceObject::SCriteriaMatchCtx CriteriaCtx(Criteria); for (i = 0; i < pSystem->GetObjectCount(); i++) { CSpaceObject *pObj = pSystem->GetObject(i); if (pObj && pObj->MatchesCriteria(CriteriaCtx, Criteria)) { Ctx.pObj = pObj; int xObj; int yObj; Ctx.XForm.Transform(pObj->GetPos(), &xObj, &yObj); pObj->Paint(Output, xObj, yObj, Ctx); } } } else { Universe.PaintPOV(Output, rcViewport, 0); } // Write to file if (!sFilespec.IsBlank()) { CString sBmpFilespec; if (iTotalCount > 100) sBmpFilespec = pathAddExtensionIfNecessary(strPatternSubst(CONSTLIT("%s%03d"), sFilespec, iSnapshotIndex + 1), CONSTLIT(".bmp")); else if (iTotalCount > 1) sBmpFilespec = pathAddExtensionIfNecessary(strPatternSubst(CONSTLIT("%s%02d"), sFilespec, iSnapshotIndex + 1), CONSTLIT(".bmp")); else sBmpFilespec = pathAddExtensionIfNecessary(sFilespec, CONSTLIT(".bmp")); CFileWriteStream OutputFile(sBmpFilespec); if (OutputFile.Create() != NOERROR) { printf("ERROR: Unable to create '%s'\n", sBmpFilespec.GetASCIIZPointer()); return; } Output.WriteToWindowsBMP(&OutputFile); OutputFile.Close(); printf("Found %s: Saved to %s\n", sTargetName.GetASCIIZPointer(), sBmpFilespec.GetASCIIZPointer()); } // Otherwise, clipboard else { if (error = Output.CopyToClipboard()) { printf("ERROR: Unable to copy image to clipboard.\n"); return; } printf("Found %s: Copied to clipboard.\n", sTargetName.GetASCIIZPointer()); } // Reset maximum loops iLoops = 20; // Done iSnapshotIndex++; if (iSnapshotIndex >= iTotalCount) break; } // Done with old system Universe.DestroySystem(pSystem); // Loop to the next node do { iNodeIndex = ((iNodeIndex + 1) % Universe.GetTopologyNodeCount()); pNode = Universe.GetTopologyNode(iNodeIndex); } while (pNode == NULL || pNode->IsEndGame()); // If we're back to the first node again, restart if (iNodeIndex == 0) { if (--iLoops > 0) { // Reinitialize Universe.Reinit(); CString sError; if (Universe.InitGame(0, &sError) != NOERROR) { printf("ERROR: %s\n", sError.GetASCIIZPointer()); return; } iNodeIndex = 0; pNode = Universe.GetTopologyNode(iNodeIndex); } else { printf("ERROR: Specified target could not be found.\n"); return; } } } }
void DoSmokeTest (CUniverse &Universe, CXMLElement *pCmdLine) { ALERROR error; int i, j; int iSystemSample = pCmdLine->GetAttributeInteger(CONSTLIT("count")); if (iSystemSample == 0) iSystemSample = DEFAULT_SYSTEM_SAMPLE; int iSystemUpdateTime = 100; // Generate systems for multiple games CSymbolTable AllSystems(TRUE, TRUE); for (i = 0; i < iSystemSample; i++) { printf("sample %d", i+1); CTopologyNode *pNode = Universe.GetFirstTopologyNode(); while (true) { // Create the system CSystem *pSystem; if (error = Universe.CreateStarSystem(pNode, &pSystem)) { printf("ERROR: Unable to create star system.\n"); return; } // Set the POV CSpaceObject *pPOV = pSystem->GetObject(0); Universe.SetPOV(pPOV); pSystem->SetPOVLRS(pPOV); // Prepare system Universe.UpdateExtended(); Universe.GarbageCollectLibraryBitmaps(); Universe.LoadLibraryBitmaps(); // Update for a while for (j = 0; j < iSystemUpdateTime; j++) Universe.Update(g_SecondsPerUpdate, true); // Get the next node CString sEntryPoint; pNode = pSystem->GetStargateDestination(CONSTLIT("Outbound"), &sEntryPoint); if (pNode == NULL || pNode->IsEndGame()) break; // Done with old system Universe.DestroySystem(pSystem); printf("."); } Universe.Reinit(); printf("\n"); } // Done printf("Test successful.\n"); }