diff --git a/src/Symfony/Bridge/Twig/CHANGELOG.md b/src/Symfony/Bridge/Twig/CHANGELOG.md index 397134150c318..8d5d6f56b6771 100644 --- a/src/Symfony/Bridge/Twig/CHANGELOG.md +++ b/src/Symfony/Bridge/Twig/CHANGELOG.md @@ -4,6 +4,7 @@ CHANGELOG 3.4.0 ----- + * added an `only` keyword to `form_theme` tag to disable usage of default themes when rendering a form * deprecated `Symfony\Bridge\Twig\Form\TwigRenderer` * deprecated `DebugCommand::set/getTwigEnvironment`. Pass an instance of `Twig\Environment` as first argument of the constructor instead diff --git a/src/Symfony/Bridge/Twig/Form/TwigRendererEngine.php b/src/Symfony/Bridge/Twig/Form/TwigRendererEngine.php index 7e375f45e2996..59120ee552d78 100644 --- a/src/Symfony/Bridge/Twig/Form/TwigRendererEngine.php +++ b/src/Symfony/Bridge/Twig/Form/TwigRendererEngine.php @@ -124,9 +124,11 @@ protected function loadResourceForBlockName($cacheKey, FormView $view, $blockNam // Check the default themes once we reach the root view without success if (!$view->parent) { - for ($i = count($this->defaultThemes) - 1; $i >= 0; --$i) { - $this->loadResourcesFromTheme($cacheKey, $this->defaultThemes[$i]); - // CONTINUE LOADING (see doc comment) + if (!isset($this->useDefaultThemes[$cacheKey]) || $this->useDefaultThemes[$cacheKey]) { + for ($i = count($this->defaultThemes) - 1; $i >= 0; --$i) { + $this->loadResourcesFromTheme($cacheKey, $this->defaultThemes[$i]); + // CONTINUE LOADING (see doc comment) + } } } diff --git a/src/Symfony/Bridge/Twig/Node/FormThemeNode.php b/src/Symfony/Bridge/Twig/Node/FormThemeNode.php index a66a13adc0287..8fcd9380a620a 100644 --- a/src/Symfony/Bridge/Twig/Node/FormThemeNode.php +++ b/src/Symfony/Bridge/Twig/Node/FormThemeNode.php @@ -22,9 +22,9 @@ */ class FormThemeNode extends Node { - public function __construct(Node $form, Node $resources, $lineno, $tag = null) + public function __construct(Node $form, Node $resources, $lineno, $tag = null, $only = false) { - parent::__construct(array('form' => $form, 'resources' => $resources), array(), $lineno, $tag); + parent::__construct(array('form' => $form, 'resources' => $resources), array('only' => (bool) $only), $lineno, $tag); } public function compile(Compiler $compiler) @@ -44,6 +44,8 @@ public function compile(Compiler $compiler) ->subcompile($this->getNode('form')) ->raw(', ') ->subcompile($this->getNode('resources')) + ->raw(', ') + ->raw(false === $this->getAttribute('only') ? 'true' : 'false') ->raw(");\n"); } } diff --git a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3HorizontalLayoutTest.php b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3HorizontalLayoutTest.php index 5625b09411ff6..e5ee8903efe4a 100644 --- a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3HorizontalLayoutTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3HorizontalLayoutTest.php @@ -99,8 +99,8 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->renderer->renderBlock($view, 'form_end', $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } } diff --git a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3LayoutTest.php b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3LayoutTest.php index 68f42a411a576..5e872b83eb67d 100644 --- a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3LayoutTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap3LayoutTest.php @@ -119,8 +119,8 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->renderer->renderBlock($view, 'form_end', $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } } diff --git a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4HorizontalLayoutTest.php b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4HorizontalLayoutTest.php index d7afc2cf26238..063edd889aed4 100644 --- a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4HorizontalLayoutTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4HorizontalLayoutTest.php @@ -100,8 +100,8 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->renderer->renderBlock($view, 'form_end', $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } } diff --git a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4LayoutTest.php b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4LayoutTest.php index 0dfa1ebadbe39..d3822ee77796a 100644 --- a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4LayoutTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionBootstrap4LayoutTest.php @@ -122,8 +122,8 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->renderer->renderBlock($view, 'form_end', $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } } diff --git a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionDivLayoutTest.php b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionDivLayoutTest.php index f65cdea0253c8..75d6f1e0504b8 100644 --- a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionDivLayoutTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionDivLayoutTest.php @@ -193,9 +193,9 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->renderer->renderBlock($view, 'form_end', $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } public static function themeBlockInheritanceProvider() diff --git a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionTableLayoutTest.php b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionTableLayoutTest.php index 594084787fff2..5119480d90e4c 100644 --- a/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionTableLayoutTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Extension/FormExtensionTableLayoutTest.php @@ -120,8 +120,8 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->renderer->renderBlock($view, 'form_end', $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } } diff --git a/src/Symfony/Bridge/Twig/Tests/Node/FormThemeTest.php b/src/Symfony/Bridge/Twig/Tests/Node/FormThemeTest.php index 05d6507fd7438..7ad445f02e6e5 100644 --- a/src/Symfony/Bridge/Twig/Tests/Node/FormThemeTest.php +++ b/src/Symfony/Bridge/Twig/Tests/Node/FormThemeTest.php @@ -39,6 +39,7 @@ public function testConstructor() $this->assertEquals($form, $node->getNode('form')); $this->assertEquals($resources, $node->getNode('resources')); + $this->assertFalse($node->getAttribute('only')); } public function testCompile() @@ -60,7 +61,17 @@ public function testCompile() $this->assertEquals( sprintf( - '$this->env->getRuntime("Symfony\\\\Component\\\\Form\\\\FormRenderer")->setTheme(%s, array(0 => "tpl1", 1 => "tpl2"));', + '$this->env->getRuntime("Symfony\\\\Component\\\\Form\\\\FormRenderer")->setTheme(%s, array(0 => "tpl1", 1 => "tpl2"), true);', + $this->getVariableGetter('form') + ), + trim($compiler->compile($node)->getSource()) + ); + + $node = new FormThemeNode($form, $resources, 0, null, true); + + $this->assertEquals( + sprintf( + '$this->env->getRuntime("Symfony\\\\Component\\\\Form\\\\FormRenderer")->setTheme(%s, array(0 => "tpl1", 1 => "tpl2"), false);', $this->getVariableGetter('form') ), trim($compiler->compile($node)->getSource()) @@ -72,7 +83,17 @@ public function testCompile() $this->assertEquals( sprintf( - '$this->env->getRuntime("Symfony\\\\Component\\\\Form\\\\FormRenderer")->setTheme(%s, "tpl1");', + '$this->env->getRuntime("Symfony\\\\Component\\\\Form\\\\FormRenderer")->setTheme(%s, "tpl1", true);', + $this->getVariableGetter('form') + ), + trim($compiler->compile($node)->getSource()) + ); + + $node = new FormThemeNode($form, $resources, 0, null, true); + + $this->assertEquals( + sprintf( + '$this->env->getRuntime("Symfony\\\\Component\\\\Form\\\\FormRenderer")->setTheme(%s, "tpl1", false);', $this->getVariableGetter('form') ), trim($compiler->compile($node)->getSource()) diff --git a/src/Symfony/Bridge/Twig/Tests/TokenParser/FormThemeTokenParserTest.php b/src/Symfony/Bridge/Twig/Tests/TokenParser/FormThemeTokenParserTest.php index 0972b15e23fdc..cd9a34cab67b9 100644 --- a/src/Symfony/Bridge/Twig/Tests/TokenParser/FormThemeTokenParserTest.php +++ b/src/Symfony/Bridge/Twig/Tests/TokenParser/FormThemeTokenParserTest.php @@ -100,6 +100,21 @@ public function getTestsForFormTheme() 'form_theme' ), ), + array( + '{% form_theme form with ["tpl1", "tpl2"] only %}', + new FormThemeNode( + new NameExpression('form', 1), + new ArrayExpression(array( + new ConstantExpression(0, 1), + new ConstantExpression('tpl1', 1), + new ConstantExpression(1, 1), + new ConstantExpression('tpl2', 1), + ), 1), + 1, + 'form_theme', + true + ), + ), ); } } diff --git a/src/Symfony/Bridge/Twig/TokenParser/FormThemeTokenParser.php b/src/Symfony/Bridge/Twig/TokenParser/FormThemeTokenParser.php index 12c2541851e63..3ead804e7e6ca 100644 --- a/src/Symfony/Bridge/Twig/TokenParser/FormThemeTokenParser.php +++ b/src/Symfony/Bridge/Twig/TokenParser/FormThemeTokenParser.php @@ -37,10 +37,15 @@ public function parse(Token $token) $stream = $this->parser->getStream(); $form = $this->parser->getExpressionParser()->parseExpression(); + $only = false; if ($this->parser->getStream()->test(Token::NAME_TYPE, 'with')) { $this->parser->getStream()->next(); $resources = $this->parser->getExpressionParser()->parseExpression(); + + if ($this->parser->getStream()->nextIf(Token::NAME_TYPE, 'only')) { + $only = true; + } } else { $resources = new ArrayExpression(array(), $stream->getCurrent()->getLine()); do { @@ -50,7 +55,7 @@ public function parse(Token $token) $stream->expect(Token::BLOCK_END_TYPE); - return new FormThemeNode($form, $resources, $lineno, $this->getTag()); + return new FormThemeNode($form, $resources, $lineno, $this->getTag(), $only); } /** diff --git a/src/Symfony/Bundle/FrameworkBundle/Templating/Helper/FormHelper.php b/src/Symfony/Bundle/FrameworkBundle/Templating/Helper/FormHelper.php index 7c695d8df3b09..f7c2b2c6986bb 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Templating/Helper/FormHelper.php +++ b/src/Symfony/Bundle/FrameworkBundle/Templating/Helper/FormHelper.php @@ -49,12 +49,13 @@ public function getName() * * The theme format is ":". * - * @param FormView $view A FormView instance - * @param string|array $themes A theme or an array of theme + * @param FormView $view A FormView instance + * @param string|array $themes A theme or an array of theme + * @param bool $useDefaultThemes If true, will use default themes defined in the renderer */ - public function setTheme(FormView $view, $themes) + public function setTheme(FormView $view, $themes, $useDefaultThemes = true) { - $this->renderer->setTheme($view, $themes); + $this->renderer->setTheme($view, $themes, $useDefaultThemes); } /** diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperDivLayoutTest.php b/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperDivLayoutTest.php index 74bdd81604d4e..b86d54b78cdb4 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperDivLayoutTest.php +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperDivLayoutTest.php @@ -121,9 +121,9 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->engine->get('form')->end($view, $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->engine->get('form')->setTheme($view, $themes); + $this->engine->get('form')->setTheme($view, $themes, $useDefaultThemes); } public static function themeBlockInheritanceProvider() diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperTableLayoutTest.php b/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperTableLayoutTest.php index 1e67134c8cb27..8dd6fffa79f41 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperTableLayoutTest.php +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Templating/Helper/FormHelperTableLayoutTest.php @@ -122,8 +122,8 @@ protected function renderEnd(FormView $view, array $vars = array()) return (string) $this->engine->get('form')->end($view, $vars); } - protected function setTheme(FormView $view, array $themes) + protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true) { - $this->engine->get('form')->setTheme($view, $themes); + $this->engine->get('form')->setTheme($view, $themes, $useDefaultThemes); } } diff --git a/src/Symfony/Component/Form/AbstractRendererEngine.php b/src/Symfony/Component/Form/AbstractRendererEngine.php index 7519011225282..ab39f1fed309b 100644 --- a/src/Symfony/Component/Form/AbstractRendererEngine.php +++ b/src/Symfony/Component/Form/AbstractRendererEngine.php @@ -33,6 +33,11 @@ abstract class AbstractRendererEngine implements FormRendererEngineInterface */ protected $themes = array(); + /** + * @var array + */ + protected $useDefaultThemes = array(); + /** * @var array */ @@ -57,13 +62,16 @@ public function __construct(array $defaultThemes = array()) /** * {@inheritdoc} */ - public function setTheme(FormView $view, $themes) + public function setTheme(FormView $view, $themes /*, $useDefaultThemes = true */) { $cacheKey = $view->vars[self::CACHE_KEY_VAR]; // Do not cast, as casting turns objects into arrays of properties $this->themes[$cacheKey] = is_array($themes) ? $themes : array($themes); + $args = func_get_args(); + $this->useDefaultThemes[$cacheKey] = isset($args[2]) ? (bool) $args[2] : true; + // Unset instead of resetting to an empty array, in order to allow // implementations (like TwigRendererEngine) to check whether $cacheKey // is set at all. diff --git a/src/Symfony/Component/Form/CHANGELOG.md b/src/Symfony/Component/Form/CHANGELOG.md index 62c52a897d3f2..19105b9e4db98 100644 --- a/src/Symfony/Component/Form/CHANGELOG.md +++ b/src/Symfony/Component/Form/CHANGELOG.md @@ -7,6 +7,8 @@ CHANGELOG * added `DebugCommand` * deprecated `ChoiceLoaderInterface` implementation in `TimezoneType` * added options "input" and "regions" to `TimezoneType` + * added an option to ``Symfony\Component\Form\FormRendererEngineInterface::setTheme()`` and + ``Symfony\Component\Form\FormRendererInterface::setTheme()`` to disable usage of default themes when rendering a form 3.3.0 ----- diff --git a/src/Symfony/Component/Form/Extension/Templating/TemplatingRendererEngine.php b/src/Symfony/Component/Form/Extension/Templating/TemplatingRendererEngine.php index 72b0a4f3dfa3a..16249c6067e81 100644 --- a/src/Symfony/Component/Form/Extension/Templating/TemplatingRendererEngine.php +++ b/src/Symfony/Component/Form/Extension/Templating/TemplatingRendererEngine.php @@ -72,9 +72,11 @@ protected function loadResourceForBlockName($cacheKey, FormView $view, $blockNam // Check the default themes once we reach the root form without success if (!$view->parent) { - for ($i = count($this->defaultThemes) - 1; $i >= 0; --$i) { - if ($this->loadResourceFromTheme($cacheKey, $blockName, $this->defaultThemes[$i])) { - return true; + if (!isset($this->useDefaultThemes[$cacheKey]) || $this->useDefaultThemes[$cacheKey]) { + for ($i = count($this->defaultThemes) - 1; $i >= 0; --$i) { + if ($this->loadResourceFromTheme($cacheKey, $blockName, $this->defaultThemes[$i])) { + return true; + } } } } diff --git a/src/Symfony/Component/Form/FormRenderer.php b/src/Symfony/Component/Form/FormRenderer.php index 8234b45f94437..c8a9d1812eb8b 100644 --- a/src/Symfony/Component/Form/FormRenderer.php +++ b/src/Symfony/Component/Form/FormRenderer.php @@ -70,9 +70,10 @@ public function getEngine() /** * {@inheritdoc} */ - public function setTheme(FormView $view, $themes) + public function setTheme(FormView $view, $themes /*, $useDefaultThemes = true */) { - $this->engine->setTheme($view, $themes); + $args = func_get_args(); + $this->engine->setTheme($view, $themes, isset($args[2]) ? (bool) $args[2] : true); } /** diff --git a/src/Symfony/Component/Form/FormRendererEngineInterface.php b/src/Symfony/Component/Form/FormRendererEngineInterface.php index 9d116b8608846..dcc15b6a2450f 100644 --- a/src/Symfony/Component/Form/FormRendererEngineInterface.php +++ b/src/Symfony/Component/Form/FormRendererEngineInterface.php @@ -21,11 +21,13 @@ interface FormRendererEngineInterface /** * Sets the theme(s) to be used for rendering a view and its children. * - * @param FormView $view The view to assign the theme(s) to - * @param mixed $themes The theme(s). The type of these themes - * is open to the implementation. + * @param FormView $view The view to assign the theme(s) to + * @param mixed $themes The theme(s). The type of these themes + * is open to the implementation. + * @param bool $useDefaultThemes If true, will use default themes specified + * in the engine, will be added to the interface in 4.0 */ - public function setTheme(FormView $view, $themes); + public function setTheme(FormView $view, $themes /*, $useDefaultThemes = true */); /** * Returns the resource for a block name. diff --git a/src/Symfony/Component/Form/FormRendererInterface.php b/src/Symfony/Component/Form/FormRendererInterface.php index 34c7822455c19..33530aeb82c47 100644 --- a/src/Symfony/Component/Form/FormRendererInterface.php +++ b/src/Symfony/Component/Form/FormRendererInterface.php @@ -28,11 +28,13 @@ public function getEngine(); /** * Sets the theme(s) to be used for rendering a view and its children. * - * @param FormView $view The view to assign the theme(s) to - * @param mixed $themes The theme(s). The type of these themes - * is open to the implementation. + * @param FormView $view The view to assign the theme(s) to + * @param mixed $themes The theme(s). The type of these themes + * is open to the implementation. + * @param bool $useDefaultThemes If true, will use default themes specified + * in the renderer, will be added to the interface in 4.0 */ - public function setTheme(FormView $view, $themes); + public function setTheme(FormView $view, $themes /*, $useDefaultThemes = true */); /** * Renders a named block of the form theme. diff --git a/src/Symfony/Component/Form/Tests/AbstractLayoutTest.php b/src/Symfony/Component/Form/Tests/AbstractLayoutTest.php index 98d2d48cbe360..4f2afa6644226 100644 --- a/src/Symfony/Component/Form/Tests/AbstractLayoutTest.php +++ b/src/Symfony/Component/Form/Tests/AbstractLayoutTest.php @@ -125,7 +125,7 @@ abstract protected function renderStart(FormView $view, array $vars = array()); abstract protected function renderEnd(FormView $view, array $vars = array()); - abstract protected function setTheme(FormView $view, array $themes); + abstract protected function setTheme(FormView $view, array $themes, $useDefaultThemes = true); public function testLabel() {