Compare commits

..

2 Commits

Author SHA1 Message Date
cb56c7d0ad Add a counter to the user menu item 2025-11-26 05:32:17 +01:00
42ac813b6f Add a counter for invitations awaiting reply 2025-11-25 16:58:19 +01:00
10 changed files with 45 additions and 45 deletions

View File

@@ -0,0 +1,6 @@
kind: Feature
body: Add a counter for invitations awaiting reply
time: 2025-11-25T16:58:11.780678466+01:00
custom:
Issue: "459"
SchemaChange: No schema change

View File

@@ -1,6 +0,0 @@
kind: UX
body: Improve accessibility of event form
time: 2025-11-26T13:39:10.462348982+01:00
custom:
Issue: "474"
SchemaChange: No schema change

View File

@@ -11,6 +11,7 @@ declare(strict_types=1);
namespace Chill\CalendarBundle\Menu;
use Chill\CalendarBundle\Repository\InviteRepository;
use Chill\MainBundle\Routing\LocalMenuBuilderInterface;
use Knp\Menu\MenuItem;
use Symfony\Component\Security\Core\Security;
@@ -18,10 +19,12 @@ use Symfony\Contracts\Translation\TranslatorInterface;
class UserMenuBuilder implements LocalMenuBuilderInterface
{
public function __construct(private readonly Security $security, public TranslatorInterface $translator) {}
public function __construct(private readonly Security $security, public TranslatorInterface $translator, private readonly InviteRepository $inviteRepository) {}
public function buildMenu($menuId, MenuItem $menu, array $parameters)
{
$invitationsPending = $this->inviteRepository->countPendingInvitesByUser($this->security->getUser());
if ($this->security->isGranted('ROLE_USER')) {
$menu->addChild('My calendar list', [
'route' => 'chill_calendar_calendar_list_my',
@@ -30,12 +33,14 @@ class UserMenuBuilder implements LocalMenuBuilderInterface
'order' => 8,
'icon' => 'tasks',
]);
$menu->addChild('invite.list.title', [
'route' => 'chill_calendar_invitations_list_my',
])
$menu->addChild(
$this->translator->trans('invite.menu with counter', ['nb' => $invitationsPending]),
['route' => 'chill_calendar_invitations_list_my']
)
->setExtras([
'order' => 9,
'icon' => 'tasks',
'counter' => 0 < $invitationsPending ? $invitationsPending : null,
]);
}
}

View File

@@ -75,6 +75,25 @@ class InviteRepository implements ObjectRepository
->getSingleScalarResult();
}
public function countPendingInvitesByUser(User $user): int
{
$qb = $this->entityRepository->createQueryBuilder('i');
$qb->select('COUNT(i)')
->where(
$qb->expr()->andX(
$qb->expr()->eq('i.user', ':user'),
$qb->expr()->eq('i.status', ':status')
)
)
->setParameters([
'user' => $user,
'status' => Invite::PENDING,
]);
return $qb->getQuery()->getSingleScalarResult();
}
public function buildAcceptedInviteByUserAndDateRangeQuery(User $user, \DateTimeImmutable $from, \DateTimeImmutable $to)
{
$qb = $this->entityRepository->createQueryBuilder('i');

View File

@@ -6,3 +6,11 @@ chill_calendar:
few {# rendez-vous sont ignorés par le filtre de date. Modifiez le filtre de date pour les voir apparaitre.}
other {# rendez-vous sont ignorés par le filtre de date. Modifiez le filtre de date pour les voir apparaitre.}
}
invite:
menu with counter: >-
{nb, plural,
=0 {Mes invitations}
one {# invitation}
few {# invitations}
other {# invitations}
}

View File

@@ -96,6 +96,7 @@ invite:
list:
none: Il n'y aucun invitation
title: Mes invitations
number of invitations waiting: Invitations en attente
# exports
Exports of calendar: Exports des rendez-vous

View File

@@ -486,7 +486,7 @@ final class ParticipationController extends AbstractController
return $this->redirectToRoute(
'chill_event__event_show',
['id' => $event->getId()]
['event_id' => $event->getId()]
);
}

View File

@@ -15,6 +15,7 @@
{{ form_row(edit_form.circle) }}
{{ form_row(edit_form.name) }}
{{ form_row(edit_form.date) }}
{{ form_row(edit_form.type, { label: "Event type" }) }}
{{ form_row(edit_form.themes) }}
{{ form_row(edit_form.moderator) }}

View File

@@ -37,9 +37,4 @@ class ChillDateTimeType extends AbstractType
{
return DateTimeType::class;
}
public function getBlockPrefix(): string
{
return 'chill_datetime';
}
}

View File

@@ -311,32 +311,3 @@
</div>
</div>
{% endblock %}
{% block chill_datetime_label %}
<label for="{{ form.date.vars.id }}" class="col-form-label col-sm-4 required">
{{ "Date"|trans }}
</label>
{% endblock %}
{% block chill_datetime_widget %}
<div class="col-sm-8 d-flex align-items-start gap-2">
{#date#}
{{ form_widget(form.date, {
attr: { class: 'form-control', style: 'flex: 1 1 auto;' }
}) }}
{#time#}
{{ form_widget(form.time, {
attr: {
class: 'form-select',
style: 'flex: 0 0 200px; max-width: 200px; white-space: nowrap; padding:0;'
}
}) }}
</div>
{% endblock %}
{% block chill_datetime_row %}
<div class="mb-3 row">
{{ block('chill_datetime_label') }}
{{ block('chill_datetime_widget') }}
</div>
{% endblock %}