<?php declare(strict_types=1);
namespace Neon\Configurator\Subscribers;
use Neon\Configurator\Neon6Configurator;
use Neon\Configurator\Services\Calculators\CalculationContext;
use Neon\Configurator\Services\Calculators\DeliverytimeCalculator;
use Neon\Configurator\Services\ConfigurationLoader;
use Shopware\Core\Content\Cms\CmsPageEntity;
use Shopware\Core\Content\Cms\Events\CmsPageLoadedEvent;
use Shopware\Core\Content\Cms\SalesChannel\Struct\BuyBoxStruct;
use Shopware\Core\Content\Cms\SalesChannel\Struct\ProductBoxStruct;
use Shopware\Core\Content\Cms\SalesChannel\Struct\ProductSliderStruct;
use Shopware\Core\Content\Product\SalesChannel\SalesChannelProductEntity;
use Shopware\Core\System\DeliveryTime\DeliveryTimeEntity;
use Shopware\Core\System\SalesChannel\SalesChannelContext;
use Shopware\Storefront\Page\PageLoadedEvent;
use Shopware\Storefront\Page\Product\ProductPageLoadedEvent;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
class OnPageLoaded implements EventSubscriberInterface
{
/** @var ConfigurationLoader */
private $configurationLoader;
/** @var DeliverytimeCalculator */
private $deliverytimeCalculator;
private $fieldDataBuilder;
/**
* @inheritDoc
*/
public static function getSubscribedEvents()
{
return [
ProductPageLoadedEvent::class => 'onPageLoaded',
CmsPageLoadedEvent::class => 'onCmsPageLoaded'
];
}
public function __construct(ConfigurationLoader $configurationLoader,
$deliverytimeCalculator,
$fieldDataBuilder)
{
$this->configurationLoader = $configurationLoader;
$this->deliverytimeCalculator = $deliverytimeCalculator;
$this->fieldDataBuilder = $fieldDataBuilder;
}
public function onPageLoaded(PageLoadedEvent $event)
{
/**
* @var SalesChannelProductEntity $product
*/
$product = $event->getPage()->getProduct();
$this->loadConfigurationFromCustomField($product, $event->getSalesChannelContext());
}
public function onCmsPageLoaded(CmsPageLoadedEvent $event)
{
/** @var CmsPageEntity $r */
foreach ($event->getResult() as $r) {
foreach ($r->getSections() as $s) {
foreach ($s->getBlocks() as $b) {
foreach ($b->getSlots() as $sl) {
if ($sl->getData() instanceof ProductBoxStruct ||
$sl->getData() instanceof BuyBoxStruct) {
/** @var ProductBoxStruct $productStruct */
$productStruct = $sl->getData();
$this->loadConfigurationFromCustomField($productStruct->getProduct(), $event->getSalesChannelContext());
}
if ($sl->getData() instanceof ProductSliderStruct) {
/** @var ProductSliderStruct $productSliderStruct */
$productSliderStruct = $sl->getData();
foreach ($productSliderStruct->getProducts() as $product) {
$this->loadConfigurationFromCustomField($product, $event->getSalesChannelContext());
}
}
}
}
}
}
}
/**
* @param SalesChannelProductEntity|null $product
* @param SalesChannelContext $context
* @return void
* @throws \Twig\Error\LoaderError
* @throws \Twig\Error\SyntaxError
*/
private function loadConfigurationFromCustomField($product, SalesChannelContext $context): void
{
if ($product != null) {
$configuration = $this->configurationLoader->loadFullConfigurationByProduct($product, $context);
$customFields = $product->getCustomFields();
$customFields[Neon6Configurator::CUSTOMFIELD_PRODUCTS_CONFIG] = $configuration;
$product->setCustomFields($customFields);
if ($configuration != null) {
$calculationContext = new CalculationContext($product,
$product->getCalculatedPrice()->getUnitPrice(),
$product->getExtension('neon_configurator')->get('properties'),
$context->getCurrentCustomerGroup(),
$this->fieldDataBuilder->buildFromDefaultValues($configuration->getFields(), $product),
$product->getMinPurchase(),
$configuration->getCommoncalculations(),
$context);
$deliveryTime = $this->deliverytimeCalculator->calculatetDeliverytime($configuration, $calculationContext);
if ($deliveryTime !== null) {
$deliveryTimeEntity = new DeliveryTimeEntity();
$deliveryTimeEntity->setMin($deliveryTime->getMin());
$deliveryTimeEntity->setMax($deliveryTime->getMax());
$deliveryTimeEntity->setUnit($deliveryTime->getUnit());
$product->setDeliveryTime($deliveryTimeEntity);
}
}
}
}
}