TYPO3 v15 dev-main snapshot ()
This commit is contained in:
@@ -0,0 +1,45 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/*
|
||||
* This file is part of the TYPO3 CMS project.
|
||||
*
|
||||
* It is free software; you can redistribute it and/or modify it under
|
||||
* the terms of the GNU General Public License, either version 2
|
||||
* of the License, or any later version.
|
||||
*
|
||||
* For the full copyright and license information, please read the
|
||||
* LICENSE.txt file that was distributed with this source code.
|
||||
*
|
||||
* The TYPO3 project - inspiring people to share!
|
||||
*/
|
||||
|
||||
/*
|
||||
* Inspired by and partially taken from the Neos.Form package (www.neos.io)
|
||||
*/
|
||||
|
||||
namespace TYPO3\CMS\Form\Domain\Renderer;
|
||||
|
||||
use TYPO3\CMS\Form\Domain\Runtime\FormRuntime;
|
||||
|
||||
/**
|
||||
* Abstract renderer which can be used as base class for custom renderers.
|
||||
*
|
||||
* Scope: frontend
|
||||
* **This class is meant to be sub classed by developers**.
|
||||
*/
|
||||
abstract class AbstractElementRenderer implements RendererInterface
|
||||
{
|
||||
protected FormRuntime $formRuntime;
|
||||
|
||||
public function setFormRuntime(FormRuntime $formRuntime): void
|
||||
{
|
||||
$this->formRuntime = $formRuntime;
|
||||
}
|
||||
|
||||
public function getFormRuntime(): FormRuntime
|
||||
{
|
||||
return $this->formRuntime;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,182 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/*
|
||||
* This file is part of the TYPO3 CMS project.
|
||||
*
|
||||
* It is free software; you can redistribute it and/or modify it under
|
||||
* the terms of the GNU General Public License, either version 2
|
||||
* of the License, or any later version.
|
||||
*
|
||||
* For the full copyright and license information, please read the
|
||||
* LICENSE.txt file that was distributed with this source code.
|
||||
*
|
||||
* The TYPO3 project - inspiring people to share!
|
||||
*/
|
||||
|
||||
/*
|
||||
* Inspired by and partially taken from the Neos.Form package (www.neos.io)
|
||||
*/
|
||||
|
||||
namespace TYPO3\CMS\Form\Domain\Renderer;
|
||||
|
||||
use Psr\EventDispatcher\EventDispatcherInterface;
|
||||
use Symfony\Component\DependencyInjection\Attribute\Autoconfigure;
|
||||
use TYPO3\CMS\Core\View\ViewFactoryData;
|
||||
use TYPO3\CMS\Core\View\ViewFactoryInterface;
|
||||
use TYPO3\CMS\Fluid\View\FluidViewAdapter;
|
||||
use TYPO3\CMS\Form\Domain\Exception\RenderingException;
|
||||
use TYPO3\CMS\Form\Event\BeforeRenderableIsRenderedEvent;
|
||||
use TYPO3\CMS\Form\ViewHelpers\RenderRenderableViewHelper;
|
||||
|
||||
/**
|
||||
* A fluid RendererInterface implementation used to render a *FormDefinition*.
|
||||
*
|
||||
* This renderer is called from {@link \TYPO3\CMS\Form\Domain\Runtime\FormRuntime::render()}.
|
||||
*
|
||||
* Options
|
||||
* =======
|
||||
*
|
||||
* The FluidFormRenderer uses some rendering options which are of particular
|
||||
* importance, as they determine how the form field is resolved to a path
|
||||
* in the file system.
|
||||
*
|
||||
* All rendering options are retrieved from the FormDefinition,
|
||||
* using the {@link \TYPO3\CMS\Form\Domain\Model\FormDefinition::getRenderingOptions()}
|
||||
* method.
|
||||
*
|
||||
* templateRootPaths
|
||||
* -----------------
|
||||
*
|
||||
* Used to define several paths for templates, which will be tried in reversed
|
||||
* order (the paths are searched from bottom to top). The first folder where
|
||||
* the desired layout is found, is used. If the array keys are numeric,
|
||||
* they are first sorted and then tried in reversed order.
|
||||
* Within this paths, fluid will search for a file which is named like the
|
||||
* renderable *type*.
|
||||
* For example:
|
||||
* templateRootPaths.10 = EXT:form/Resources/Private/Frontend/Templates/
|
||||
* $renderable->getType() = Form
|
||||
* Expected template file: EXT:form/Resources/Private/Frontend/Templates/Form.html
|
||||
* There is a setting available to set a custom template name. Please read
|
||||
* the section 'templateName'.
|
||||
*
|
||||
* Only the root renderable (FormDefinition) has to be a template file.
|
||||
* All child renderables are partials. By default, the root renderable
|
||||
* is called 'Form'.
|
||||
*
|
||||
* layoutRootPaths
|
||||
* ---------------
|
||||
*
|
||||
* Used to define several paths for layouts, which will be tried in reversed
|
||||
* order (the paths are searched from bottom to top). The first folder where
|
||||
* the desired layout is found, is used. If the array keys are numeric,
|
||||
* they are first sorted and then tried in reversed order.
|
||||
*
|
||||
* partialRootPaths
|
||||
* ----------------
|
||||
*
|
||||
* Used to define several paths for partials, which will be tried in reversed
|
||||
* order. The first folder where the desired partial is found, is used.
|
||||
* The keys of the array define the order.
|
||||
*
|
||||
* Within this paths, fluid will search for a file which is named like the
|
||||
* renderable *type*.
|
||||
* For example:
|
||||
* templateRootPaths.10 = EXT:form/Resources/Private/Frontend/Partials/
|
||||
* $renderable->getType() = Text
|
||||
* Expected template file: EXT:form/Resources/Private/Frontend/Partials/Text.html
|
||||
* There is a setting available to set a custom partial name. Please read
|
||||
* the section 'templateName'.
|
||||
*
|
||||
* templateName
|
||||
* -----------
|
||||
* By default, the renderable type will be taken as the name for the
|
||||
* template / partial.
|
||||
* For example:
|
||||
* partialRootPaths.10 = EXT:form/Resources/Private/Frontend/Partials/
|
||||
* $renderable->getType() = Text
|
||||
* Expected partial file: EXT:form/Resources/Private/Frontend/Partials/Text.html
|
||||
*
|
||||
* Set 'templateName' to define a custom name which should be used instead.
|
||||
* For example:
|
||||
* templateName = Foo
|
||||
* $renderable->getType() = Text
|
||||
* Expected partial file: EXT:form/Resources/Private/Frontend/Partials/Foo.html
|
||||
*
|
||||
* Rendering Child Renderables
|
||||
* ===========================
|
||||
*
|
||||
* If a renderable wants to render child renderables, inside its template / partial,
|
||||
* it can do that using the <code><formvh:renderRenderable></code> ViewHelper.
|
||||
*
|
||||
* A template example from Page shall demonstrate this:
|
||||
*
|
||||
* <pre>
|
||||
* <formvh:renderRenderable renderable="{page}">
|
||||
* <f:for each="{page.elements}" as="element">
|
||||
* <formvh:renderRenderable renderable="{element}">
|
||||
* <f:render partial="{element.templateName}" arguments="{element: element}" />
|
||||
* </formvh:renderRenderable>
|
||||
* </f:for>
|
||||
* </formvh:renderRenderable>
|
||||
* </pre>
|
||||
*
|
||||
* Scope: frontend
|
||||
* **This class is NOT meant to be sub classed by developers.**
|
||||
* @internal
|
||||
*/
|
||||
#[Autoconfigure(public: true, shared: false)]
|
||||
class FluidFormRenderer extends AbstractElementRenderer
|
||||
{
|
||||
public function __construct(
|
||||
protected readonly ViewFactoryInterface $viewFactory,
|
||||
private readonly EventDispatcherInterface $eventDispatcher,
|
||||
) {}
|
||||
|
||||
/**
|
||||
* Renders the FormDefinition.
|
||||
*
|
||||
* This method is expected to call the 'beforeRendering' hook
|
||||
* on each renderable.
|
||||
* This method call the 'beforeRendering' hook initially.
|
||||
* Each other hooks will be called from the
|
||||
* renderRenderable viewHelper.
|
||||
* {@link \TYPO3\CMS\Form\ViewHelpers\RenderRenderableViewHelper::render()}
|
||||
*
|
||||
* @return string the rendered $formRuntime
|
||||
* @internal
|
||||
*/
|
||||
public function render(): string
|
||||
{
|
||||
$formElementType = $this->formRuntime->getType();
|
||||
$renderingOptions = $this->formRuntime->getRenderingOptions();
|
||||
if (!isset($renderingOptions['templateRootPaths']) || !is_array($renderingOptions['templateRootPaths'])) {
|
||||
throw new RenderingException(sprintf('The option templateRootPaths must be set for renderable "%s"', $formElementType), 1480293084);
|
||||
}
|
||||
if (!isset($renderingOptions['layoutRootPaths']) || !is_array($renderingOptions['layoutRootPaths'])) {
|
||||
throw new RenderingException(sprintf('The option layoutRootPaths must be set for renderable "%s"', $formElementType), 1480293085);
|
||||
}
|
||||
if (!isset($renderingOptions['partialRootPaths']) || !is_array($renderingOptions['partialRootPaths'])) {
|
||||
throw new RenderingException(sprintf('The option partialRootPaths must be set for renderable "%s"', $formElementType), 1480293086);
|
||||
}
|
||||
$viewFactoryData = new ViewFactoryData(
|
||||
templateRootPaths: $renderingOptions['templateRootPaths'],
|
||||
partialRootPaths: $renderingOptions['partialRootPaths'],
|
||||
layoutRootPaths: $renderingOptions['layoutRootPaths'],
|
||||
request: $this->getFormRuntime()->getRequest(),
|
||||
);
|
||||
$view = $this->viewFactory->create($viewFactoryData);
|
||||
$view->assign('form', $this->formRuntime);
|
||||
if ($view instanceof FluidViewAdapter) {
|
||||
// @todo: Find a different solution than setting this state here. This happens in other
|
||||
// ext:form places as well and should vanish to be more non-fluid view friendly.
|
||||
$view->getRenderingContext()
|
||||
->getViewHelperVariableContainer()
|
||||
->addOrUpdate(RenderRenderableViewHelper::class, 'formRuntime', $this->formRuntime);
|
||||
}
|
||||
$this->eventDispatcher->dispatch(new BeforeRenderableIsRenderedEvent($this->formRuntime->getFormDefinition(), $this->formRuntime));
|
||||
return $view->render($this->formRuntime->getTemplateName());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/*
|
||||
* This file is part of the TYPO3 CMS project.
|
||||
*
|
||||
* It is free software; you can redistribute it and/or modify it under
|
||||
* the terms of the GNU General Public License, either version 2
|
||||
* of the License, or any later version.
|
||||
*
|
||||
* For the full copyright and license information, please read the
|
||||
* LICENSE.txt file that was distributed with this source code.
|
||||
*
|
||||
* The TYPO3 project - inspiring people to share!
|
||||
*/
|
||||
|
||||
/*
|
||||
* Inspired by and partially taken from the Neos.Form package (www.neos.io)
|
||||
*/
|
||||
|
||||
namespace TYPO3\CMS\Form\Domain\Renderer;
|
||||
|
||||
use TYPO3\CMS\Form\Domain\Runtime\FormRuntime;
|
||||
|
||||
/**
|
||||
* Base interface for Renderers. A Renderer is used to render a form.
|
||||
*
|
||||
* Scope: frontend
|
||||
* **This interface is meant to be implemented by developers, although often you
|
||||
* will subclass AbstractElementRenderer** ({@link AbstractElementRenderer}).
|
||||
*/
|
||||
interface RendererInterface
|
||||
{
|
||||
/**
|
||||
* Note: This method is expected to call the 'beforeRendering' hook
|
||||
* on each $renderable
|
||||
*
|
||||
* @return string the rendered $formRuntime
|
||||
*/
|
||||
public function render(): string;
|
||||
|
||||
public function setFormRuntime(FormRuntime $formRuntime): void;
|
||||
|
||||
public function getFormRuntime(): FormRuntime;
|
||||
}
|
||||
Reference in New Issue
Block a user