Using autocompletes
The SyliusBootstrapAdminUi package uses Symfony UX under the hood. Thus, UX autocomplete is already setup and configured in your admin panel. This means that any simple ChoiceType filter form can be turned into an autocomplete simply by setting autocomplete to true in form options.
public function configureOptions(OptionsResolver $resolver): void
{
$resolver->setDefaults([
'choices' => $this->getChoices(),
'placeholder' => 'sylius.ui.all',
'autocomplete' => true,
]);
}
public function getParent(): string
{
return ChoiceType::class;
}
However, if your autocomplete filter requires fetching data from another entity, you will need to use a BaseEntityAutocompleteType in order to fetch your options via AJAX.
All you need to start leveraging this functionality is a bit of routing config.
Configure the entity autocomplete route
<?php
declare(strict_types=1);
use Symfony\Component\Routing\Loader\Configurator\RoutingConfigurator;
return static function (RoutingConfigurator $routingConfigurator): void {
// ...
$routingConfigurator
->add('ux_entity_autocomplete_admin', '/admin/autocomplete/{alias}')
->controller('ux.autocomplete.entity_autocomplete_controller')
;
};
This adds a new ux_entity_autocomplete_admin AJAX route dedicated to your autocompletes.
Add a grid filter with entity autocomplete
First, you need to create an entity autocomplete field .
<?php
declare(strict_types=1);
namespace App\Form;
use App\Entity\Speaker;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\UX\Autocomplete\Form\AsEntityAutocompleteField;
use Symfony\UX\Autocomplete\Form\BaseEntityAutocompleteType;
#[AsEntityAutocompleteField(
alias: 'app_admin_speaker',
route: 'ux_entity_autocomplete_admin', // Use the route you just configured.
)]
final class SpeakerAutocompleteType extends AbstractType
{
public function configureOptions(OptionsResolver $resolver): void
{
$resolver->setDefaults([
'class' => Speaker::class,
'choice_label' => 'fullName',
]);
}
public function getParent(): string
{
return BaseEntityAutocompleteType::class;
}
}Then, you need to create your grid filter.
<?php
declare(strict_types=1);
namespace App\Grid\Filter;
use App\Form\SpeakerAutocompleteType;
use Sylius\Component\Grid\Attribute\AsFilter;
use Sylius\Component\Grid\Data\DataSourceInterface;
use Sylius\Component\Grid\Filter\EntityFilter;
use Sylius\Component\Grid\Filtering\FilterInterface;
#[AsFilter(
formType: SpeakerAutocompleteType::class,
template: '@SyliusBootstrapAdminUi/shared/grid/filter/select.html.twig', // optional
)]
final class SpeakerFilter implements FilterInterface
{
public function __construct(
private readonly EntityFilter $entityFilter,
) {
}
public function apply(DataSourceInterface $dataSource, string $name, mixed $data, array $options): void
{
$this->entityFilter->apply($dataSource, $name, $data, $options);
}
}Now that the filter is configured, you can use it inside any grid.
<?php
declare(strict_types=1);
namespace App\Grid;
use App\Grid\Filter\SpeakerFilter;
use Sylius\Bundle\GridBundle\Builder\Filter\Filter;
use Sylius\Bundle\GridBundle\Builder\GridBuilderInterface;
use Sylius\Bundle\GridBundle\Grid\AbstractGrid;
use Sylius\Bundle\GridBundle\Grid\ResourceAwareGridInterface;
use Sylius\Component\Grid\Attribute\AsGrid;
#[AsGrid(resourceClass: Talk::class)]
final class TalkGrid extends AbstractGrid
{
// ...
public function __invoke(GridBuilderInterface $gridBuilder): void
{
$gridBuilder
// ...
->addFilter(
Filter::create(name: 'speaker', type: SpeakerFilter::class)
->setLabel('app.ui.speaker')
->setOptions(['fields' => ['speakers.id']]),
)
// ...
;
}
// ...
}Last updated