Implement snip tags with very elegant tags form
This commit is contained in:
@ -28,6 +28,7 @@ class SnipType extends AbstractType
|
||||
'attr' => ['rows' => 20],
|
||||
'mapped' => false,
|
||||
])
|
||||
->add('tags', TagsType::class)
|
||||
->add('public', SwitchType::class)
|
||||
->add('visible', SwitchType::class)
|
||||
;
|
||||
|
79
src/Form/TagsType.php
Normal file
79
src/Form/TagsType.php
Normal file
@ -0,0 +1,79 @@
|
||||
<?php
|
||||
|
||||
namespace App\Form;
|
||||
|
||||
use App\Entity\Tag;
|
||||
use App\Repository\TagRepository;
|
||||
use Doctrine\Common\Collections\Collection;
|
||||
use Symfony\Bundle\SecurityBundle\Security;
|
||||
use Symfony\Component\Form\AbstractType;
|
||||
use Symfony\Component\Form\DataTransformerInterface;
|
||||
use Symfony\Component\Form\Extension\Core\Type\TextType;
|
||||
use Symfony\Component\Form\FormBuilderInterface;
|
||||
use Symfony\Component\OptionsResolver\OptionsResolver;
|
||||
|
||||
class TagsType extends AbstractType implements DataTransformerInterface
|
||||
{
|
||||
public function __construct(
|
||||
private readonly TagRepository $repository,
|
||||
private readonly Security $security,
|
||||
) {}
|
||||
|
||||
public function transform($value): string
|
||||
{
|
||||
if ($value === null) {
|
||||
return '';
|
||||
}
|
||||
|
||||
if ($value instanceof Collection) {
|
||||
$value = $value->toArray();
|
||||
}
|
||||
|
||||
if (is_array($value)) {
|
||||
$tags = array_map(fn(Tag $tag) => $tag->getName(), $value);
|
||||
} else {
|
||||
return '';
|
||||
}
|
||||
return implode(', ', $tags);
|
||||
}
|
||||
|
||||
public function reverseTransform($value): array
|
||||
{
|
||||
$tags = array_filter(array_map('trim', explode(',', $value)));
|
||||
$user = $this->security->getUser();
|
||||
|
||||
$tagEntities = [];
|
||||
foreach ($tags as $tag) {
|
||||
$tagEntity = $this->repository->findOneBy(['name' => $tag, 'user' => $user]);
|
||||
if ($tagEntity === null) {
|
||||
$tagEntity = new Tag()
|
||||
->setName($tag)
|
||||
->setUser($user)
|
||||
;
|
||||
$this->repository->save($tagEntity);
|
||||
}
|
||||
$tagEntities[] = $tagEntity;
|
||||
}
|
||||
|
||||
return $tagEntities;
|
||||
}
|
||||
|
||||
public function buildForm(FormBuilderInterface $builder, array $options): void
|
||||
{
|
||||
$builder->addModelTransformer($this);
|
||||
}
|
||||
|
||||
public function configureOptions(OptionsResolver $resolver): void
|
||||
{
|
||||
$resolver->setDefaults([
|
||||
'data_class' => null, // No specific entity class
|
||||
'label' => 'Tags (comma-separated)',
|
||||
'attr' => ['class' => 'tags-input'], // Optional: Add custom attributes
|
||||
]);
|
||||
}
|
||||
|
||||
public function getParent(): string
|
||||
{
|
||||
return TextType::class;
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user