<?php
/**
* Created by PhpStorm.
* User: michael
* Date: 04/02/2019
* Time: 15:39
*/
namespace App\Controller\Front;
use App\Entity\Store;
use App\Repository\StoreRepository;
use App\Service\GmapsService;
use App\Service\RefereeService;
use App\Service\StoreService;
use Geocoder\Exception\Exception;
use Http\Discovery\Exception\NotFoundException;
use Knp\Component\Pager\PaginatorInterface;
use Psr\Log\LoggerInterface;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
use Symfony\Component\Routing\Annotation\Route;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Request;
class StoreFinderController extends AbstractController
{
/**
* Lister les centres auditifs sur la page de recherche
*
* @Route(
* "/finder",
* name="find_nearest_store",
* methods={"GET", "POST"},
* options = { "expose" = true }
* )
* @param Request $request
* @param PaginatorInterface $paginator
* @param GmapsService $gmapsService
* @param RefereeService $refereeService
* @param LoggerInterface $logger
* @param StoreRepository $storeRepository
* @param StoreService $storeService
* @return Response
* @throws Exception
*/
public function findNearestStore(Request $request, PaginatorInterface $paginator, GmapsService $gmapsService, RefereeService $refereeService, LoggerInterface $logger, StoreRepository $storeRepository, StoreService $storeService): Response
{
if($request->query->has('page') && !is_numeric($request->query->get('page'))){
throw new NotFoundHttpException('Page not found');
}
$geocodeAddress = null;
$arrayPresentableStore = [];
$arraySelectionStore = [];
$arraySelectionSerialize = [];
if ($request->query->has('address')) {
$queryAddress = $request->get('address');
if(!empty($queryAddress) && $queryAddress != "null") {
// geocoding par adresse
$logger->info('get address by geocoding : ' . $queryAddress);
$geocodeAddress = $gmapsService->getCoordinateFromAddress($queryAddress);
} else if($request->query->has('lat') && $request->query->has('lng')) {
// reverse geocoding par lat/lng
$queryLat = $request->get('lat');
$queryLng = $request->get('lng');
$logger->info('get address by reverse geocoding : ' . $queryLat . ' ; ' . $queryLng);
$geocodeAddress = $gmapsService->getAddressFromCoordinates($queryLat, $queryLng);
}
}
if ($geocodeAddress !== null && !$geocodeAddress->isEmpty()) {
$latitude = $geocodeAddress->first()->getCoordinates()->getLatitude();
$longitude = $geocodeAddress->first()->getCoordinates()->getLongitude();
//store lat/long for later use (display direction on store page map)
$request->getSession()->set('finder_coordinates', [$latitude, $longitude]);
$logger->info('find store for address : lat(' . $latitude . ') / lng(' . $longitude . ')');
$storeAndDistance = $storeRepository->findActiveStoresAroundLocation($latitude, $longitude, $request->query->get('area_search', Store::AREA_SEARCH));
if (!empty($storeAndDistance)) {
foreach ($storeAndDistance as $storeWithDistance) {
// tableau des stores présentables sérialisés pour la vue
$arrayPresentableStore[$storeWithDistance[0]->getId()] = $storeService->serializeStoreForView($storeWithDistance[0], $storeWithDistance['distance']);
}
if($request->query->getInt('page', 1) == 1) {
// afficher la selection MCA uniquement sur la page 1
$arraySelectionStore = $refereeService->getHightligthStore($latitude, $longitude);
}
foreach ($arraySelectionStore as $selectedStoreWithDistance) {
$selectedStoreId = $selectedStoreWithDistance['store']->getId();
// retirer la selection de liste des stores présentables
unset($arrayPresentableStore[$selectedStoreId]);
// tableau des store selectionnés sérialisés pour la vue
$arraySelectionSerialize[$selectedStoreId] = $storeService->serializeStoreForView($selectedStoreWithDistance['store'], $selectedStoreWithDistance['distance_reel']);
}
// pagination des stores pour la vue
$paginatorOnStore = $paginator->paginate(
$arrayPresentableStore,
$request->query->getInt('page', 1),
Store::NUM_STORE_PER_PAGE,
array('wrap-queries' => true)
);
return $this->render('front_v4/mca/store/finder.html.twig', [
'stores' => $paginatorOnStore->getItems(),
'pagination' => $paginatorOnStore,
'preferred_stores' => $arraySelectionSerialize,
'formatted_address_query' => $geocodeAddress->first()->getFormattedAddress(),
'city_address_query' => $geocodeAddress->first()->getLocality()
]);
}
// aucun store trouvé
return $this->render('front_v4/mca/store/finder.html.twig', [
'stores' => null,
'pagination' => null,
'preferred_stores' => null,
'formatted_address_query' => $geocodeAddress->first()->getFormattedAddress(),
'city_address_query' => $geocodeAddress->first()->getLocality()
]);
}
// adresse invalide
$logger->info('no address found');
return $this->render('front_v4/mca/store/finder.html.twig', [
'stores' => null,
'pagination' => null,
'preferred_stores' => null,
'formatted_address_query' => '',
'city_address_query' => ''
]);
}
}