<?php declare(strict_types=1); namespace vonRotenberg\RealEstateListingBundle\Controller\FrontendModule; use vonRotenberg\RealEstateListingBundle\Model\ManagedPropertyModel; use Contao\ArrayUtil; use Contao\CoreBundle\Controller\FrontendModule\AbstractFrontendModuleController; use Contao\CoreBundle\DependencyInjection\Attribute\AsFrontendModule; use Contao\CoreBundle\Exception\ResponseException; use Contao\CoreBundle\Image\Studio\Figure; use Contao\CoreBundle\Image\Studio\FigureBuilder; use Contao\CoreBundle\Twig\FragmentTemplate; use Contao\File; use Contao\FilesModel; use Contao\Input; use Contao\ModuleModel; use Contao\PageModel; use Contao\StringUtil; use Contao\System; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpFoundation\Response; #[AsFrontendModule(category: 'vr_real_estate')] class ManagedPropertyController extends AbstractFrontendModuleController { public const TYPE = 'managed_property'; protected function getResponse(FragmentTemplate $template, ModuleModel $model, Request $request): Response { $arrAssets = []; $arrFilterOptions = [ 'city' => [] ]; $arrFilterSelected = []; $arrAssetsOptions = []; $jumpTo = PageModel::findByPk($model->jumpTo); $urlGenerator = System::getContainer()->get('contao.routing.content_url_generator'); // Filter if (isset($_GET['filter']) && \is_array(Input::get('filter'))) { foreach (Input::get('filter') as $filter=>$value) { if (in_array($filter, array_keys($arrFilterOptions)) && !empty($value)) { $rawValue = StringUtil::decodeEntities($value); $arrFilterSelected[$filter] = $rawValue; if (preg_match('/^.*<>.*$/',$rawValue)) { list($start,$stop) = preg_split('/<>/',$rawValue, 2); $arrAssetsOptions['column'][$filter] = "$filter BETWEEN $start AND $stop"; } else { $arrAssetsOptions['column'][$filter] = "$filter = ?"; $arrAssetsOptions['value'][$filter] = $rawValue; } } } } if (($assets = ManagedPropertyModel::findAllPublished(0,0,$arrAssetsOptions)) === null) { return $template->getResponse(); } // Figure Builder $figureBuilder = System::getContainer() ->get('contao.image.studio') ->createFigureBuilder() ->setSize($model->imgSize) ->setLightboxGroupIdentifier('lb' . $model->id); foreach ($assets as $asset) { $arrItem = array_merge($asset->row(), [ 'teaserFigure' => $this->getImageFigures($asset->gallerySRC, $figureBuilder, $asset->orderSRC, 1), 'detailsUrl' => $jumpTo !== null ? $urlGenerator->generate($jumpTo, ['parameters'=>'/items/'.$asset->id]) : null ]); $arrAssets[] = $arrItem; } // Populate filters $filterAssets = ManagedPropertyModel::findAllPublished(); foreach ($filterAssets as $asset) { // Filter options if (!empty($asset->city)) { $tmpOptions = $arrAssetsOptions; $tmpOptions['column'] = array_merge((isset($arrAssetsOptions['column']) ? $arrAssetsOptions['column'] : []),['city'=>'city = ?']); $tmpOptions['value'] = array_merge((isset($arrAssetsOptions['value']) ? $arrAssetsOptions['value'] : []),['city'=>$asset->city]); $count = ManagedPropertyModel::countAllPublished($tmpOptions); $arrFilterOptions['city'][$asset->city] = $asset->city . ' ('.$count.')'; } } foreach (array_keys($arrFilterOptions) as $filterName) { $arrFilterOptions[$filterName] = array_unique($arrFilterOptions[$filterName]); } // Set template data $template->set('filterOptions',$arrFilterOptions); $template->set('filter',$arrFilterSelected); $template->set('assets',$arrAssets); // Handle ajax if ($request->headers->get('VR-Ajax') == 'RePropertiesList') { throw new ResponseException($template->getResponse()); } return $template->getResponse(); } /** * @param string|array $strUuids * @param FigureBuilder $figureBuilder * @param string|array $strOrder * * @return array|Figure * @throws \Exception */ public function getImageFigures($strUuids, $figureBuilder, $strOrder = null, int $intLimit = 0, int $intOffset = 0) { $arrImageFigures = []; if (($imageFiles = FilesModel::findMultipleByUuids(StringUtil::deserialize($strUuids))) !== null) { $images = array(); while ($imageFiles->next()) { // Continue if the files has been processed or does not exist if (isset($images[$imageFiles->path]) || !file_exists(System::getContainer()->getParameter('kernel.project_dir') . '/' . $imageFiles->path)) { continue; } // Single files if ($imageFiles->type == 'file') { $objFile = new File($imageFiles->path); if (!$objFile->isImage) { continue; } // Add the image $images[$imageFiles->path] = $imageFiles->current(); } // Folders else { $objSubfiles = FilesModel::findByPid($imageFiles->uuid, array('order' => 'name')); if ($objSubfiles === null) { continue; } while ($objSubfiles->next()) { // Skip subfolders if ($objSubfiles->type == 'folder') { continue; } $objFile = new File($objSubfiles->path); if (!$objFile->isImage) { continue; } // Add the image $images[$objSubfiles->path] = $objSubfiles->current(); } } } if ($strOrder !== null) { $images = ArrayUtil::sortByOrderField($images, $strOrder); } $images = array_values($images); // Offset images if ($intOffset > 0) { $images = \array_slice($images, ($intOffset < count($images) ? $intOffset : count($images))); } // Limit number of images if ($intLimit > 0) { $images = \array_slice($images, 0, $intLimit); } // Build figures of images foreach ($images as $image) { $figure = $figureBuilder ->fromFilesModel($image) ->build(); $arrImageFigures[] = $figure; } } return count ($arrImageFigures) === 1 && $intLimit === 1 ? array_shift($arrImageFigures) : $arrImageFigures; } }