/** * Generate a new galaxy. * * @return \Illuminate\Http\RedirectResponse */ public function generate() { // Start with a clean slate. DB::table('stars')->delete(); DB::table('star_links')->delete(); // Create new stars. $starCount = 200; /** * @var Star[] $unvisitedStars * @var Star[] $visitedStars * @var Star[] $allStars */ $unvisitedStars = []; $visitedStars = []; $allStars = []; for ($i = 0; $i < $starCount; $i++) { $star = new Star(['name' => $this->generateName()]); $star->save(); $unvisitedStars[$star->getKey()] = true; $allStars[$star->getKey()] = $star; } // Create links between stars. $totalLinks = 0; $starId = array_rand($allStars); $visitedStars[$starId] = $allStars[$starId]; unset($unvisitedStars[$starId]); // Random walk to generate a uniform spanning tree. while (!empty($unvisitedStars)) { $star = $visitedStars[$starId]; $otherStarId = array_rand($allStars); $otherStar = $allStars[$otherStarId]; if (!isset($visitedStars[$otherStarId])) { $star->exits()->attach($otherStar); $otherStar->exits()->attach($star); $visitedStars[$otherStarId] = $allStars[$otherStarId]; unset($unvisitedStars[$otherStarId]); $totalLinks++; } $starId = $otherStarId; } // Add some extra links to create cycles. for ($i = 0; $i < $totalLinks / 10; $i++) { $star = $allStars[array_rand($allStars)]; $otherStar = $allStars[array_rand($allStars)]; if ($star != $otherStar) { $star->exits()->attach($otherStar); $otherStar->exits()->attach($star); $totalLinks++; } } return redirect()->back()->with('status', 'Generated ' . $starCount . ' stars and ' . $totalLinks . ' star links.'); }
/** * Generate the starting ship for all players. * * @param User $player * * @return Ship */ public static function getStartingShip(User $player) { $ship = new Ship(['name' => self::randomShipName()]); // Start with an 'Explorer' class hip. $shipType = ShipType::whereName('Explorer')->first(); $ship->type()->associate($shipType); // Place it at a random star. $star = Star::findStartLocation(); $ship->location()->associate($star); // Give it to the player. $ship->owner()->associate($player); $ship->save(); // Add a jumpstore and a cargo item. $item = JumpStore::whereValue(1)->get()->random(); $ship->items()->attach($item, ['amount' => 1]); switch (mt_rand(0, 2)) { case 0: $item = BiologyCargo::whereValue(1)->get()->random(); break; case 1: $item = TechnologyCargo::whereValue(1)->get()->random(); break; case 2: $item = LuxuryCargo::whereValue(1)->get()->random(); break; } $ship->items()->attach($item, ['amount' => 1]); // Start with a bit of money and full energy. $ship->credits = 1000; $ship->energy = $ship->energy_capacity; $ship->structure = $shipType->structure; $ship->save(); return $ship; }