Ajax Request mittels Extbase und Fluid
# Extensionname: hkfewo
# Pluginbezeichner: ajax
plugin.tx_hkfewo_ajax {
settings {
typeNum = 230130
}
}
# PAGE object for Ajax call:
hkfewo_page = PAGE
hkfewo_page {
typeNum = 230130
config {
disableAllHeaderCode = 1
additionalHeaders = Content-type:application/html
xhtml_cleaning = 0
debug = 0
no_cache = 1
admPanel = 0
}
10 < tt_content.list.20.hkfewo_ajax
}
Dem Ajax-Request eine Adresse zuweisen, unter der auch getesetet werden kann
PageTypeSuffix:
type: PageType
default: ''
map:
'ajax.html': 230130
In der ext_localconf das Plugin definieren
/**
* Plugin- Ajax
*/
\TYPO3\CMS\Extbase\Utility\ExtensionUtility::configurePlugin(
'HkFewo',
'Ajax',
[
\HK\HkFewo\Controller\AjaxController::class => 'getPrice',
],
[
\HK\HkFewo\Controller\AjaxController::class => 'getPrice',
]
);
Im Fluid den Action-Link in einem versteckten Element erstellen, damit dieser über das Attr data-url ausgelesen werden kann
<a class="button ajaxButton getNewPrice" data-page="{page}" data-url="{f:uri.action(action: 'getPrice', controller: 'Ajax', pluginName: 'Ajax', pageType:'230130', arguments:'{posted: posted}')}"></a>
<div id="showPrice">
<!-- Container, der das Ergebnis des Ajax-Requests anzeigen wird -->
</div>
Ajax-Request per jQuery
// fireAjaxEvent an ein jQuery Event (click, onload, change, ...) binden und darüber aufrufen.
function fireAjaxEvent () {
// den Action-Link aus dem versteckten Element holen
var url = $(".ajaxButton.getNewPrice").attr('data-url');
var format = 'html';
var betten = parseInt(parseInt($("#buchungsanfrage-personen_erwachsene").val()) + parseInt($("#buchungsanfrage-personen_kinder_gross").val()));
$.ajax
({
type: "POST",
url: url + "&tx_hkfewo_ajax%5Bposted%5D%5Bdate_von%5D=" + $("#date_von").val() + "&tx_hkfewo_ajax%5Bposted%5D%5Bdate_bis%5D=" + $("#date_bis").val() + "&tx_hkfewo_ajax%5BnewDate%5D%5Bdate_von%5D=" + $("#date_von").val() + "&tx_hkfewo_ajax%5BnewDate%5D%5Bdate_bis%5D=" + $("#date_bis").val() + "&tx_hkfewo_ajax%5Bbetten%5D=" + betten + "&tx_hkfewo_ajax%5Bhaustiere%5D=" + $("#buchungsanfrage-haustier").val() + "&tx_hkfewo_ajax%5Bservice1_zusatz%5D=" + $("#buchungsanfrage-service1_zusatz").val(),
headers: {
'Cache-Control': 'no-cache, no-store, must-revalidate',
'Pragma': 'no-cache',
'Expires': '0'
},
dataType: format,
success: function (result)
{
// Aufbereitetes Ergebnis aus Ajax-Template an Ziel-Container übergeben
$("#showPrice").html(result);
},
error: function (e)
{
console.log('Error: ' + e);
}
});
};
Ajax-Controller, der die Berechnungen durchführt und die Werte per assign an das Ajax-FluidTemplate weitergibt
<?php
namespace HK\HkFewo\Controller;
use TYPO3\CMS\Extbase\Utility\DebuggerUtility;
use TYPO3\CMS\Core\Utility\GeneralUtility;
use HK\HkFewo\Domain\Model\Objekt;
class AjaxController extends \TYPO3\CMS\Extbase\Mvc\Controller\ActionController {
/**
* @var \HK\HkFewo\Domain\Repository\ObjektRepository
* @TYPO3\CMS\Extbase\Annotation\Inject
*/
protected $_ObjektRepository = null;
/**
* @var \HK\HkFewo\Domain\Repository\SaisonRepository
* @TYPO3\CMS\Extbase\Annotation\Inject
*/
protected $_SaisonRepository = null;
/**
* @var \HK\HkFewo\Domain\Repository\ObjektpreiseRepository
* @TYPO3\CMS\Extbase\Annotation\Inject
*/
protected $_ObjektpreiseRepository = null;
/**
* @var \HK\HkFewo\Domain\Repository\KonfigurationRepository
* @TYPO3\CMS\Extbase\Annotation\Inject
*/
protected $_KonfigurationRepository = null;
protected function initializeAction() {
parent::initializeAction();
/** @var $querySettings QuerySettingsInterface */
$querySettings = GeneralUtility::makeInstance(\TYPO3\CMS\Extbase\Persistence\Generic\Typo3QuerySettings::class);
$querySettings->setStoragePageIds([180]);
$this->_ObjektRepository->setDefaultQuerySettings($querySettings);
$this->_SaisonRepository->setDefaultQuerySettings($querySettings);
$this->_ObjektpreiseRepository->setDefaultQuerySettings($querySettings);
$this->_KonfigurationRepository->setDefaultQuerySettings($querySettings);
}
public function getPriceAction() {
$posted = $this->request->getArgument('posted');
if ($this->request->hasArgument('newDate')) {
$newDate = $this->request->getArgument('newDate');
}
$objekt = $this->_ObjektRepository->findByUid(intval($posted['objekt']));
$plannedStart = new \DateTime();
$plannedEnd = new \DateTime();
if ($newDate['date_von']) {
$dateVon = $newDate['date_von'];
} else {
$dateVon = $posted['date_von'];
}
if ($newDate['date_bis']) {
$dateBis = $newDate['date_bis'];
} else {
$dateBis = $posted['date_bis'];
}
if ($dateVon && $dateBis) {
$planned_start = $dateVon;
$planned_end = $dateBis;
$plannedStart = \DateTime::createFromFormat('d.m.Y', $planned_start);
$plannedEnd = \DateTime::createFromFormat('d.m.Y', $planned_end);
}
$plannedStart->setTime(0, 0, 0);
$plannedEnd->setTime(0, 0, 0);
$fullprice = 0;
$alldays = 0;
$pricePerDay = 0;
if ($plannedEnd > $plannedStart) {
$saisonartArrayDateRange = $this->_SaisonRepository->findByDateRange($plannedStart, $plannedEnd);
$daysPerSaisonart = array_filter(array_count_values($saisonartArrayDateRange), function ($v) {
return $v > 0;
});
$saisonprice = $objekt->getCurrentPreise()->processSaisonPreise();
foreach ($daysPerSaisonart as $saisonart => $days) {
$fullprice += ($days * $saisonprice[$saisonart]);
$alldays += $days;
}
$pricePerDay = $fullprice / $alldays;
}
$price['fullprice'] = $fullprice;
$price['alldays'] = $alldays;
$price['pricePerDay'] = $pricePerDay;
$price['daysPerSaisonart'] = $daysPerSaisonart;
$gesamtpreis = $price['fullprice'];
# Waeschekosten laden
$waescheKosten = $this->_KonfigurationRepository->getValueAsFloat('waesche');
if ($this->request->hasArgument('betten')) {
$bettenMin = $objekt->getDetails()[0]->getSchlafplaetze();
$bettenMax = $objekt->getDetails()[0]->getSchlafplaetzeBis() ? $objekt->getDetails()[0]->getSchlafplaetzeBis() : $objekt->getDetails()[0]->getSchlafplaetze();
$betten = $this->request->getArgument('betten');
if ($betten > $bettenMin) {
$zusaetzlicheBetten = $betten - $bettenMin;
$price['zusaetzlicheBetten'] = $zusaetzlicheBetten;
$price['waeschekosten'] = $zusaetzlicheBetten * $waescheKosten;
$gesamtpreis += $price['waeschekosten'];
}
}
$haustierKosten = $this->_KonfigurationRepository->getValueAsFloat('haustier');
if ($this->request->hasArgument('haustiere')) {
$haustiere = $this->request->getArgument('haustiere');
if ($haustiere > 0) {
$price['haustiere'] = $haustiere;
$price['haustierkosten'] = $haustiere * $haustierKosten;
$gesamtpreis += $price['haustierkosten'];
}
}
$kinderbettKosten = $this->_KonfigurationRepository->getValueAsFloat('kinderbett');
if ($this->request->hasArgument('service1_zusatz')) {
$kinderbetten = $this->request->getArgument('service1_zusatz');
if ($kinderbetten > 0) {
$price['kinderbetten'] = $kinderbetten;
$price['kinderbettkosten'] = $kinderbetten * $kinderbettKosten;
$gesamtpreis += $price['kinderbettkosten'];
}
}
$price['gesamtpreis'] = $gesamtpreis;
$this->view->assign('data', $price);
}
}
Fluid-Plugin, das die per AjaxController ermittelten Werte über ein html-Template ausgiebt
<strong>Voraussichtlicher Preis: <f:format.currency currencySign="€" decimalSeparator="," thousandsSeparator=".">{data.gesamtpreis}</f:format.currency></strong> <br />
<f:format.currency currencySign="€" decimalSeparator="," thousandsSeparator=".">{data.fullprice}</f:format.currency> für {data.alldays} Nächte<br />
<f:if condition="{data.zusaetzlicheBetten} && {data.waeschekosten} > 0">
{data.zusaetzlicheBetten} zusätzliche{f:if(condition:'{data.zusaetzlicheBetten}==1',then:'s')} Wäschepaket{f:if(condition:'{data.zusaetzlicheBetten}>1',then:'e')}: <f:format.currency currencySign="€" decimalSeparator="," thousandsSeparator=".">{data.waeschekosten}</f:format.currency></br />
</f:if>
<f:if condition="{data.kinderbetten} && {data.kinderbettkosten} > 0">
{data.kinderbetten} Kinderbett{f:if(condition:'{data.kinderbetten}>1',then:'en')}: <f:format.currency currencySign="€" decimalSeparator="," thousandsSeparator=".">{data.kinderbettkosten}</f:format.currency><br />
</f:if>
<f:if condition="{data.haustiere} && {data.haustierkosten} > 0">
{data.haustiere} Haustier{f:if(condition:'{data.haustiere}>1',then:'e')}: <f:format.currency currencySign="€" decimalSeparator="," thousandsSeparator=".">{data.haustierkosten}</f:format.currency><br />
</f:if>