So it seems it is necessary to extend the ViewsAutocompleteFiltersController
class to do this. In order to override the routing so that a custom controller can be used instead, an entry must be added to /mymodule/mymodule.services.yml
:
services:
mymodule.route_subscriber:
class: Drupal\mymodule\Routing\RouteSubscriber
tags:
- { name: event_subscriber }
Then provide your /mymodule/src/Routing/RouteSubscriber.php
file, which redirects to our local ViewsAutocompleteFiltersController
<?php
namespace Drupal\mymodule\Routing;
use Drupal\Core\Routing\RouteSubscriberBase;
use Symfony\Component\Routing\RouteCollection;
/**
* Listens to the dynamic route events.
*/
class RouteSubscriber extends RouteSubscriberBase {
/**
* {@inheritdoc}
*/
public function alterRoutes(RouteCollection $collection) {
// Replace "some.route.name" below with the actual route you want to override.
if ($route = $collection->get('viewsfilters.autocomplete')) {
$route->setDefaults(array(
'_controller' => '\Drupal\mymodule\Controller\ViewsAutocompleteFiltersController::autocomplete',
));
}
}
}
Finally provide your local /mymodule/src/Controller/ViewsAutocompleteFiltersController.php
which filters for the view of interest, then modifies the output of the base ViewsAutocompleteFiltersController
. The tricky part of that process is that the data
member of the JsonResponse
output is protected, so we use a customized JsonResponse
wrapper to perform the highlighting:
<?php
namespace Drupal\mymodule\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\JsonResponse;
/**
* Overrides default ViewsAutocompleteFiltersController to provide highlighting of autocomplete suggestions
*/
class ViewsAutocompleteFiltersController extends \Drupal\views_autocomplete_filters\Controller\ViewsAutocompleteFiltersController {
/**
* {@inheritdoc]
*/
public function autocomplete(Request $request, $view_name, $view_display, $filter_name, $view_args) {
$response = parent::autocomplete($request, $view_name, $view_display, $filter_name, $view_args);
if($response instanceof JsonResponse && $view_name === 'my_view' && $view_display === 'my_view_display') {
$response = new HighlightedJsonResponse($response, $request->query->get('q'));
}
return $response;
}
}
/**
* Overrides default JsonResponse to provide highlighting of autocomplete suggestions
*/
class HighlightedJsonResponse extends JsonResponse {
function __construct($jsonResponse, $q) {
$data = \json_decode($jsonResponse->data);
if(isset($q)) {
$qPattern = '/(' . preg_quote($q, '/') . ')/i';
foreach($data as &$datum) {
if(isset($datum->label)) {
$datum->label = '<b>' . \preg_replace($qPattern, '</b>$0<b>', $datum->label) . '</b>';
$datum->label = \str_replace("<b></b>","",$datum->label);
}
}
}
parent::__construct($data, $jsonResponse->statusCode, $jsonResponse->headers->all());
}
}