Commit b3763793 authored by alexpott's avatar alexpott

Issue #2114069 by dawehner, Gábor Hojtsy, ursula: Fixed Routing / tabs /...

Issue #2114069 by dawehner, Gábor Hojtsy, ursula: Fixed Routing / tabs / actions lack way to attach context to UI strings.
parent 4361e679
...@@ -57,8 +57,12 @@ public function getTitle(Request $request, Route $route) { ...@@ -57,8 +57,12 @@ public function getTitle(Request $request, Route $route) {
$route_title = call_user_func_array($callable, $arguments); $route_title = call_user_func_array($callable, $arguments);
} }
elseif ($title = $route->getDefault('_title')) { elseif ($title = $route->getDefault('_title')) {
$options = array();
if ($context = $route->getDefault('_title_context')) {
$options['context'] = $context;
}
// Fall back to a static string from the route. // Fall back to a static string from the route.
$route_title = $this->translationManager->translate($title); $route_title = $this->translationManager->translate($title, array(), $options);
} }
return $route_title; return $route_title;
} }
......
...@@ -27,6 +27,11 @@ ...@@ -27,6 +27,11 @@
*/ */
class ViewSubscriber implements EventSubscriberInterface { class ViewSubscriber implements EventSubscriberInterface {
/**
* The content negotiation.
*
* @var \Drupal\Core\ContentNegotiation
*/
protected $negotiation; protected $negotiation;
/** /**
...@@ -91,8 +96,8 @@ public function onView(GetResponseForControllerResultEvent $event) { ...@@ -91,8 +96,8 @@ public function onView(GetResponseForControllerResultEvent $event) {
} }
// If no title was returned fall back to one defined in the route. // If no title was returned fall back to one defined in the route.
if (!isset($page_result['#title']) && $request->attributes->has('_title')) { if (!isset($page_result['#title'])) {
$page_result['#title'] = $request->attributes->get('_title'); $page_result['#title'] = $this->titleResolver->getTitle($request, $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT));
} }
$event->setResponse(new Response(drupal_render_page($page_result))); $event->setResponse(new Response(drupal_render_page($page_result)));
...@@ -109,8 +114,8 @@ public function onView(GetResponseForControllerResultEvent $event) { ...@@ -109,8 +114,8 @@ public function onView(GetResponseForControllerResultEvent $event) {
} }
// If no title was returned fall back to one defined in the route. // If no title was returned fall back to one defined in the route.
if (!isset($page_result['#title']) && $request->attributes->has('_title')) { if (!isset($page_result['#title'])) {
$page_result['#title'] = $request->attributes->get('_title'); $page_result['#title'] = $this->titleResolver->getTitle($request, $request->attributes->get(RouteObjectInterface::ROUTE_OBJECT));
} }
$event->setResponse(new Response(drupal_render($page_result))); $event->setResponse(new Response(drupal_render($page_result)));
......
...@@ -67,7 +67,11 @@ public function getRouteName() { ...@@ -67,7 +67,11 @@ public function getRouteName() {
*/ */
public function getTitle() { public function getTitle() {
// Subclasses may pull in the request or specific attributes as parameters. // Subclasses may pull in the request or specific attributes as parameters.
return $this->t($this->pluginDefinition['title']); $options = array();
if (!empty($this->pluginDefinition['title_context'])) {
$options['context'] = $this->pluginDefinition['title_context'];
}
return $this->t($this->pluginDefinition['title'], array(), $options);
} }
/** /**
......
...@@ -75,7 +75,11 @@ public function getRouteParameters(Request $request) { ...@@ -75,7 +75,11 @@ public function getRouteParameters(Request $request) {
*/ */
public function getTitle() { public function getTitle() {
// Subclasses may pull in the request or specific attributes as parameters. // Subclasses may pull in the request or specific attributes as parameters.
return $this->t($this->pluginDefinition['title']); $options = array();
if (!empty($this->pluginDefinition['title_context'])) {
$options['context'] = $this->pluginDefinition['title_context'];
}
return $this->t($this->pluginDefinition['title'], array(), $options);
} }
/** /**
......
...@@ -115,6 +115,9 @@ public function form(array $form, array &$form_state) { ...@@ -115,6 +115,9 @@ public function form(array $form, array &$form_state) {
'%title' => $comment->subject->value, '%title' => $comment->subject->value,
)); ));
} }
else {
$form['#title'] = $this->t('Preview comment');
}
} }
else { else {
if ($this->currentUser->isAuthenticated()) { if ($this->currentUser->isAuthenticated()) {
......
...@@ -239,6 +239,8 @@ system.date_format_localize_reset: ...@@ -239,6 +239,8 @@ system.date_format_localize_reset:
system.modules_list: system.modules_list:
path: '/admin/modules' path: '/admin/modules'
defaults: defaults:
_title: 'Extend'
_title_context: 'With components'
_form: 'Drupal\system\Form\ModulesListForm' _form: 'Drupal\system\Form\ModulesListForm'
requirements: requirements:
_permission: 'administer modules' _permission: 'administer modules'
......
<?php
/**
* @file
* Contains \Drupal\Tests\Core\Controller\TitleResolverTest.
*/
namespace Drupal\Tests\Core\Controller;
use Drupal\Component\Utility\String;
use Drupal\Core\Controller\TitleResolver;
use Drupal\Tests\UnitTestCase;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Routing\Route;
/**
* Tests the title resolver.
*
* @see \Drupal\Core\Controller\TitleResolver
*/
class TitleResolverTest extends UnitTestCase {
/**
* The mocked controller resolver.
*
* @var \Drupal\Core\Controller\ControllerResolverInterface|\PHPUnit_Framework_MockObject_MockObject
*/
protected $controllerResolver;
/**
* The mocked translation manager.
*
* @var \Drupal\Core\StringTranslation\TranslationInterface|\PHPUnit_Framework_MockObject_MockObject
*/
protected $translationManager;
/**
* The actual tested title resolver.
*
* @var \Drupal\Core\Controller\TitleResolver
*/
protected $titleResolver;
public static function getInfo() {
return array(
'name' => 'Title resolver',
'description' => 'Tests the title resolver.',
'group' => 'Routing',
);
}
protected function setUp() {
$this->controllerResolver = $this->getMock('\Drupal\Core\Controller\ControllerResolverInterface');
$this->translationManager = $this->getMock('\Drupal\Core\StringTranslation\TranslationInterface');
$this->titleResolver = new TitleResolver($this->controllerResolver, $this->translationManager);
}
/**
* Tests a static title without a context.
*
* @see \Drupal\Core\Controller\TitleResolver::getTitle()
*/
public function testStaticTitle() {
$request = new Request();
$route = new Route('/test-route', array('_title' => 'static title'));
$this->translationManager->expects($this->once())
->method('translate')
->with('static title', array(), array())
->will($this->returnValue('translated title'));
$this->assertEquals('translated title', $this->titleResolver->getTitle($request, $route));
}
/**
* Tests a static title with a context.
*
* @see \Drupal\Core\Controller\TitleResolver::getTitle()
*/
public function testStaticTitleWithContext() {
$request = new Request();
$route = new Route('/test-route', array('_title' => 'static title', '_title_context' => 'context'));
$this->translationManager->expects($this->once())
->method('translate')
->with('static title', array(), array('context' => 'context'))
->will($this->returnValue('translated title with context'));
$this->assertEquals('translated title with context', $this->titleResolver->getTitle($request, $route));
}
/**
* Tests a dynamic title.
*
* @see \Drupal\Core\Controller\TitleResolver::getTitle()
*/
public function testDynamicTitle() {
$request = new Request();
$route = new Route('/test-route', array('_title' => 'static title', '_title_callback' => 'Drupal\Tests\Core\Controller\TitleCallback::example'));
$callable = array(new TitleCallback(), 'example');
$this->controllerResolver->expects($this->once())
->method('getControllerFromDefinition')
->with('Drupal\Tests\Core\Controller\TitleCallback::example')
->will($this->returnValue($callable));
$this->controllerResolver->expects($this->once())
->method('getArguments')
->with($request, $callable)
->will($this->returnValue(array('example')));
$this->assertEquals('test example', $this->titleResolver->getTitle($request, $route));
}
}
/**
* Provides an example title callback for the testDynamicTitle method above.
*/
class TitleCallback {
/**
* Gets the example string.
*
* @param string $value
* The dynamic value.
*
* @return string
* Returns the example string.
*/
public function example($value) {
return String::format('test @value', array('@value' => $value));
}
}
<?php
/**
* @file
* Contains \Drupal\Tests\Core\Menu\LocalActionDefaultTest.
*/
namespace Drupal\Tests\Core\Menu;
use Drupal\Core\DependencyInjection\ContainerBuilder;
use Drupal\Core\Menu\LocalActionDefault;
use Drupal\Tests\UnitTestCase;
/**
* Tests the local action default class.
*
* @see \Drupal\Core\Menu\LocalActionDefault
*/
class LocalActionDefaultTest extends UnitTestCase {
/**
* The tested local action default plugin.
*
* @var \Drupal\Core\Menu\LocalActionDefault
*/
protected $localActionDefault;
/**
* The used plugin configuration.
*
* @var array
*/
protected $config = array();
/**
* The used plugin ID.
*
* @var string
*/
protected $pluginId = 'local_action_default';
/**
* The used plugin definition.
*
* @var array
*/
protected $pluginDefinition = array(
'id' => 'local_action_default',
);
/**
* The mocked translator.
*
* @var \Drupal\Core\StringTranslation\TranslationInterface|\PHPUnit_Framework_MockObject_MockObject
*/
protected $stringTranslation;
/**
* The mocked route provider.
*
* @var \Drupal\Core\Routing\RouteProviderInterface|\PHPUnit_Framework_MockObject_MockObject
*/
protected $routeProvider;
public static function getInfo() {
return array(
'name' => 'Local actions default plugin.',
'description' => 'Tests the local action default class.',
'group' => 'Menu',
);
}
protected function setUp() {
parent::setUp();
$this->stringTranslation = $this->getMock('Drupal\Core\StringTranslation\TranslationInterface');
$this->routeProvider = $this->getMock('Drupal\Core\Routing\RouteProviderInterface');
}
/**
* Setups the local action default.
*/
protected function setupLocalActionDefault() {
$container = new ContainerBuilder();
$container->set('string_translation', $this->stringTranslation);
\Drupal::setContainer($container);
$this->localActionDefault = new LocalActionDefault($this->config, $this->pluginId, $this->pluginDefinition, $this->routeProvider);
}
/**
* Tests the getTitle method without a translation context.
*
* @see \Drupal\Core\Menu\LocalTaskDefault::getTitle()
*/
public function testGetTitle() {
$this->pluginDefinition['title'] = 'Example';
$this->stringTranslation->expects($this->once())
->method('translate')
->with($this->pluginDefinition['title'], array(), array())
->will($this->returnValue('Example translated'));
$this->setupLocalActionDefault();
$this->assertEquals('Example translated', $this->localActionDefault->getTitle());
}
/**
* Tests the getTitle method with a translation context.
*
* @see \Drupal\Core\Menu\LocalTaskDefault::getTitle()
*/
public function testGetTitleWithContext() {
$this->pluginDefinition['title'] = 'Example';
$this->pluginDefinition['title_context'] = 'context';
$this->stringTranslation->expects($this->once())
->method('translate')
->with($this->pluginDefinition['title'], array(), array('context' => 'context'))
->will($this->returnValue('Example translated with context'));
$this->setupLocalActionDefault();
$this->assertEquals('Example translated with context', $this->localActionDefault->getTitle());
}
}
...@@ -253,20 +253,38 @@ public function testActive() { ...@@ -253,20 +253,38 @@ public function testActive() {
} }
/** /**
* Tests the getTitle method. * Tests the getTitle method without a translation context.
* *
* @see \Drupal\Core\Menu\LocalTaskDefault::getTitle() * @see \Drupal\Core\Menu\LocalTaskDefault::getTitle()
*/ */
public function testGetTitle() { public function testGetTitle() {
$this->pluginDefinition['title'] = 'Example'; $this->pluginDefinition['title'] = 'Example';
$this->stringTranslation->expects($this->once()) $this->stringTranslation->expects($this->once())
->method('translate', $this->pluginDefinition['title']) ->method('translate')
->with($this->pluginDefinition['title'], array(), array())
->will($this->returnValue('Example translated')); ->will($this->returnValue('Example translated'));
$this->setupLocalTaskDefault(); $this->setupLocalTaskDefault();
$this->assertEquals('Example translated', $this->localTaskBase->getTitle()); $this->assertEquals('Example translated', $this->localTaskBase->getTitle());
} }
/**
* Tests the getTitle method with a translation context.
*
* @see \Drupal\Core\Menu\LocalTaskDefault::getTitle()
*/
public function testGetTitleWithContext() {
$this->pluginDefinition['title'] = 'Example';
$this->pluginDefinition['title_context'] = 'context';
$this->stringTranslation->expects($this->once())
->method('translate')
->with($this->pluginDefinition['title'], array(), array('context' => 'context'))
->will($this->returnValue('Example translated with context'));
$this->setupLocalTaskDefault();
$this->assertEquals('Example translated with context', $this->localTaskBase->getTitle());
}
/** /**
* Tests the getOption method. * Tests the getOption method.
* *
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment