feature/avoid-repeating-places-in-game #38
@ -48,10 +48,8 @@ class GameFlowController
|
|||||||
return new JsonContent(['error' => 'no_session_found']);
|
return new JsonContent(['error' => 'no_session_found']);
|
||||||
}
|
}
|
||||||
|
|
||||||
$userId = $session->get('userId');
|
|
||||||
|
|
||||||
if (!isset($state['currentRound']) || $state['currentRound'] == -1 || $state['currentRound'] >= static::NUMBER_OF_ROUNDS) {
|
if (!isset($state['currentRound']) || $state['currentRound'] == -1 || $state['currentRound'] >= static::NUMBER_OF_ROUNDS) {
|
||||||
$this->startNewGame($state, $mapId, $userId);
|
$this->startNewGame($state, $mapId);
|
||||||
$session->set('state', $state);
|
$session->set('state', $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -161,8 +159,8 @@ class GameFlowController
|
|||||||
private function saveVisit($last): void
|
private function saveVisit($last): void
|
||||||
{
|
{
|
||||||
$session = $this->request->session();
|
$session = $this->request->session();
|
||||||
|
|
||||||
$userId = $session->get('userId');
|
$userId = $session->get('userId');
|
||||||
|
|
||||||
if(isset($userId)) {
|
if(isset($userId)) {
|
||||||
$placeId = $last['placeId'];
|
$placeId = $last['placeId'];
|
||||||
$userPlayedPlace = $this->userPlayedPlaceRepository->getByUserIdAndPlaceId($userId, $placeId);
|
$userPlayedPlace = $this->userPlayedPlaceRepository->getByUserIdAndPlaceId($userId, $placeId);
|
||||||
@ -252,8 +250,11 @@ class GameFlowController
|
|||||||
return ['distance' => $distance, 'score' => $score];
|
return ['distance' => $distance, 'score' => $score];
|
||||||
}
|
}
|
||||||
|
|
||||||
private function startNewGame(array &$state, int $mapId, $userId = null): void
|
private function startNewGame(array &$state, int $mapId): void
|
||||||
{
|
{
|
||||||
|
$session = $this->request->session();
|
||||||
|
$userId = $session->get('userId'); // in case of multiplayer it will be null and handled the same way as for anonymous players
|
||||||
|
|
||||||
$places = $this->placeRepository->getRandomNPlaces($mapId, static::NUMBER_OF_ROUNDS, $userId);
|
$places = $this->placeRepository->getRandomNPlaces($mapId, static::NUMBER_OF_ROUNDS, $userId);
|
||||||
|
|
||||||
$state['rounds'] = [];
|
$state['rounds'] = [];
|
||||||
|
@ -223,8 +223,8 @@ class Select
|
|||||||
|
|
||||||
private function generateQuery(): array
|
private function generateQuery(): array
|
||||||
{
|
{
|
||||||
list($innerQuery, $innerParams) = $this->generateTable($this->table, true);
|
list($tableQuery, $tableParams) = $this->generateTable($this->table, true);
|
||||||
$queryString = 'SELECT ' . $this->generateColumns() . ' FROM ' . $innerQuery;
|
$queryString = 'SELECT ' . $this->generateColumns() . ' FROM ' . $tableQuery;
|
||||||
|
|
||||||
if (count($this->joins) > 0) {
|
if (count($this->joins) > 0) {
|
||||||
list($joinQuery, $joinParams) = $this->generateJoins();
|
list($joinQuery, $joinParams) = $this->generateJoins();
|
||||||
@ -265,7 +265,7 @@ class Select
|
|||||||
$queryString = '(' . $queryString . ') AS ' . $this->tableAliases[Select::DERIVED_TABLE_KEY];
|
$queryString = '(' . $queryString . ') AS ' . $this->tableAliases[Select::DERIVED_TABLE_KEY];
|
||||||
}
|
}
|
||||||
|
|
||||||
return [$queryString, array_merge($innerParams, $joinParams, $whereParams, $havingParams)];
|
return [$queryString, array_merge($tableParams, $joinParams, $whereParams, $havingParams)];
|
||||||
}
|
}
|
||||||
|
|
||||||
private function generateTable($table, bool $defineAlias = false): array
|
private function generateTable($table, bool $defineAlias = false): array
|
||||||
|
@ -29,11 +29,11 @@ class PlaceRepository
|
|||||||
}
|
}
|
||||||
|
|
||||||
//TODO: use Map and User instead of id
|
//TODO: use Map and User instead of id
|
||||||
public function getRandomNPlaces(int $mapId, int $n, int $userId = null): array
|
public function getRandomNPlaces(int $mapId, int $n, ?int $userId): array
|
||||||
{
|
{
|
||||||
if(!isset($userId)) {
|
if(!isset($userId)) { // anonymous single player or multiplayer game
|
||||||
return $this->getRandomNForMapWithValidPano($mapId, $n);
|
return $this->getRandomNForMapWithValidPano($mapId, $n);
|
||||||
} else {
|
} else { // authorized user
|
||||||
$unvisitedPlaces = $this->getRandomUnvisitedNForMapWithValidPano($mapId, $n, $userId);
|
$unvisitedPlaces = $this->getRandomUnvisitedNForMapWithValidPano($mapId, $n, $userId);
|
||||||
$oldPlaces = $this->getRandomOldNForMapWithValidPano($mapId, $n - count($unvisitedPlaces), $userId);
|
$oldPlaces = $this->getRandomOldNForMapWithValidPano($mapId, $n - count($unvisitedPlaces), $userId);
|
||||||
|
|||||||
return array_merge($unvisitedPlaces, $oldPlaces);
|
return array_merge($unvisitedPlaces, $oldPlaces);
|
||||||
@ -149,7 +149,7 @@ class PlaceRepository
|
|||||||
// set order by datetime, oldest first
|
// set order by datetime, oldest first
|
||||||
$selectOldPlaces->orderBy('last_time');
|
$selectOldPlaces->orderBy('last_time');
|
||||||
|
|
||||||
// selection algorithm with preference (weighting) for older places
|
// selection algorithm with preference (weighting) for older places using Box-Muller transform
|
||||||
$pickGaussianRandomInt = function($numberOfPlaces) {
|
$pickGaussianRandomInt = function($numberOfPlaces) {
|
||||||
$stdev = 0.2;
|
$stdev = 0.2;
|
||||||
$avg = 0.0;
|
$avg = 0.0;
|
||||||
|
Loading…
Reference in New Issue
Block a user
I would check if
count($unvisitedPlaces) == $n
before calling this function so we could save a function call and a DB query in a lot of cases.