feat: display teamers' average ratings in several locations

This commit is contained in:
Björn Fromme
2024-01-10 13:05:47 +01:00
parent 7215b3077b
commit 159ea37a42
9 changed files with 49 additions and 14 deletions
+17
View File
@@ -496,6 +496,23 @@ class Teamer implements TimestampableEntityInterface
return $this; return $this;
} }
public function getAverageRating(): ?int
{
$feedbackCount = $this->getFeedback()->count();
if (0 === $feedbackCount) {
return null;
}
$sum = 0;
foreach ($this->getFeedback() as $feedback) {
$sum += $feedback->getAverageRating();
}
return $sum / $feedbackCount;
}
/** /**
* @return Collection<int, TrainingAttendance> * @return Collection<int, TrainingAttendance>
*/ */
+2 -1
View File
@@ -69,8 +69,9 @@ class ApplicationRepository extends ServiceEntityRepository
$qb = $this->createQueryBuilder('application'); $qb = $this->createQueryBuilder('application');
return $qb return $qb
->select('application', 'teamer') ->select('application', 'teamer', 'feedback')
->innerJoin('application.teamer', 'teamer') ->innerJoin('application.teamer', 'teamer')
->leftJoin('teamer.feedback', 'feedback')
->where($qb->expr()->andX( ->where($qb->expr()->andX(
$qb->expr()->eq('application.assignment', ':assignment'), $qb->expr()->eq('application.assignment', ':assignment'),
$qb->expr()->neq('application.status', ':status') $qb->expr()->neq('application.status', ':status')
+2 -1
View File
@@ -96,8 +96,9 @@ class DispositionRepository extends ServiceEntityRepository
$qb = $this->createQueryBuilder('disposition'); $qb = $this->createQueryBuilder('disposition');
return $qb return $qb
->select('disposition', 'teamer') ->select('disposition', 'teamer', 'feedback')
->innerJoin('disposition.teamer', 'teamer') ->innerJoin('disposition.teamer', 'teamer')
->leftJoin('teamer.feedback', 'feedback')
->where($qb->expr()->eq('disposition.assignment', ':assignment')) ->where($qb->expr()->eq('disposition.assignment', ':assignment'))
->setParameter('assignment', $assignment) ->setParameter('assignment', $assignment)
->getQuery() ->getQuery()
+2 -1
View File
@@ -32,10 +32,11 @@ class TeamerRepository extends ServiceEntityRepository
$qb = $this->createQueryBuilder('teamer'); $qb = $this->createQueryBuilder('teamer');
$qb $qb
->select('teamer', 'user') ->select('teamer', 'user', 'feedback')
->leftJoin('teamer.availabilities', 'availability') ->leftJoin('teamer.availabilities', 'availability')
->leftJoin('teamer.jobProfiles', 'job_profile') ->leftJoin('teamer.jobProfiles', 'job_profile')
->leftJoin('teamer.licenses', 'license') ->leftJoin('teamer.licenses', 'license')
->leftJoin('teamer.feedback', 'feedback')
->leftJoin('teamer.user', 'user') ->leftJoin('teamer.user', 'user')
; ;
+5 -1
View File
@@ -89,8 +89,12 @@ class AppRuntime implements RuntimeExtensionInterface
return $this->intlExtension->formatCurrency($amount, 'EUR'); return $this->intlExtension->formatCurrency($amount, 'EUR');
} }
public function formatRating(int $rating): string public function formatRating(?int $rating): string
{ {
if (null === $rating) {
return '-';
}
// Ratings are stored as integers so divide by 100 first // Ratings are stored as integers so divide by 100 first
$rating = $rating / 100; $rating = $rating / 100;
@@ -0,0 +1,6 @@
{% set averageRating = teamer.averageRating %}
<div class="inline-flex items-center"{% if teamer.averageRating %}{{ stimulus_controller('tooltip', { content: averageRating|format_rating|raw, placement: 'top' }) }}{% endif %}>
{% for grade in range(1, 6) %}
{{ icon('star', html_classes('w-3 h-3', { 'text-gray-200': averageRating < grade * 100, 'text-primary': averageRating >= grade * 100 })) }}
{% endfor %}
</div>
@@ -134,6 +134,7 @@
<span>{{ disposition.teamer }}</span> <span>{{ disposition.teamer }}</span>
{{ icon('info', 'w-4 h-4') }} {{ icon('info', 'w-4 h-4') }}
</button> </button>
{% include '_partials/_rating_stars.html.twig' with { 'teamer': disposition.teamer } %}
</td> </td>
<td> <td>
{{ disposition.remarks|nl2br|default('-') }} {{ disposition.remarks|nl2br|default('-') }}
+12 -9
View File
@@ -59,15 +59,18 @@
{% for teamer in pagination %} {% for teamer in pagination %}
<tr> <tr>
<td> <td>
{% if teamer.photo %} <div class="flex flex-col items-center space-y-2">
<img src="{{ asset(teamer.photo.filename | imagine_filter('profile')) }}" {% if teamer.photo %}
class="w-12 h-auto rounded-full" <img src="{{ asset(teamer.photo.filename | imagine_filter('profile')) }}"
alt="{{ teamer.firstName }}"> class="w-12 h-auto rounded-full"
{% else %} alt="{{ teamer.firstName }}">
<div class="flex flex-col items-center justify-center w-12 h-12 border-2 border-gray-200 rounded-full"> {% else %}
{{ icon('user', 'w-10 h-10 text-gray-200') }} <div class="flex flex-col items-center justify-center w-12 h-12 border-2 border-gray-200 rounded-full">
</div> {{ icon('user', 'w-10 h-10 text-gray-200') }}
{% endif %} </div>
{% endif %}
{% include '_partials/_rating_stars.html.twig' with { 'teamer': teamer } %}
</div>
</td> </td>
<td> <td>
<a href="{{ path('app_admin_teamer_profile', { 'uuid': teamer.uuid }) }}"> <a href="{{ path('app_admin_teamer_profile', { 'uuid': teamer.uuid }) }}">
+2 -1
View File
@@ -29,7 +29,7 @@
{% endfor %} {% endfor %}
</ul> </ul>
</div> </div>
<div> <div class="flex flex-col space-y-4">
{% if teamer.photo %} {% if teamer.photo %}
<img src="{{ asset(teamer.photo.filename | imagine_filter('profile')) }}" <img src="{{ asset(teamer.photo.filename | imagine_filter('profile')) }}"
class="w-32 h-auto border-2 border-primary" class="w-32 h-auto border-2 border-primary"
@@ -39,5 +39,6 @@
{{ icon('user', 'w-32 h-32 text-gray-200') }} {{ icon('user', 'w-32 h-32 text-gray-200') }}
</div> </div>
{% endif %} {% endif %}
{% include '_partials/_rating_stars.html.twig' with { 'teamer': teamer } %}
</div> </div>
</div> </div>