wip: courses
This commit is contained in:
@@ -95,14 +95,15 @@ class Travel
|
|||||||
* @param mixed $group The service group(s) to filter by
|
* @param mixed $group The service group(s) to filter by
|
||||||
* @param bool $availableOnly Whether to include only available services
|
* @param bool $availableOnly Whether to include only available services
|
||||||
*
|
*
|
||||||
* @return array<Service> The filtered and sorted services array
|
* @return array<int, Service> The filtered and sorted services array
|
||||||
*/
|
*/
|
||||||
public function getAdditionalServicesByGroup(mixed $group, bool $availableOnly = true): array
|
public function getAdditionalServicesByGroup(mixed $group, bool $availableOnly = true): array
|
||||||
{
|
{
|
||||||
$group = (array) $group;
|
$group = (array) $group;
|
||||||
|
|
||||||
$services = array_filter($this->additionalServices, function (Service $service) use ($group, $availableOnly) {
|
$services = array_filter($this->additionalServices, function (Service $service) use ($group, $availableOnly) {
|
||||||
return true === in_array($service->subType, $group) && (false === $availableOnly || 0 < $service->available);
|
return true === in_array($service->subType, $group)
|
||||||
|
&& (false === $availableOnly || 0 < $service->available || null === $service->available);
|
||||||
});
|
});
|
||||||
|
|
||||||
usort($services, function (Service $a, Service $b) {
|
usort($services, function (Service $a, Service $b) {
|
||||||
@@ -121,14 +122,14 @@ class Travel
|
|||||||
* @param string $direction The travel direction to filter by
|
* @param string $direction The travel direction to filter by
|
||||||
* @param bool $availableOnly Whether to include only available services
|
* @param bool $availableOnly Whether to include only available services
|
||||||
*
|
*
|
||||||
* @return array<Service> The filtered and sorted transportation services
|
* @return array<int, Service> The filtered and sorted transportation services
|
||||||
*/
|
*/
|
||||||
public function getTransportationServicesByDirection(string $direction, bool $availableOnly = true): array
|
public function getTransportationServicesByDirection(string $direction, bool $availableOnly = true): array
|
||||||
{
|
{
|
||||||
$services = array_filter($this->transportationServices, function (Service $service) use ($direction, $availableOnly) {
|
$services = array_filter($this->transportationServices, function (Service $service) use ($direction, $availableOnly) {
|
||||||
return $direction === $service->direction
|
return $direction === $service->direction
|
||||||
&& $service->price >= 0
|
&& $service->price >= 0
|
||||||
&& (false === $availableOnly || $service->available > 0);
|
&& (false === $availableOnly || $service->available > 0 || null === $service->available);
|
||||||
});
|
});
|
||||||
|
|
||||||
usort($services, function (Service $a, Service $b) {
|
usort($services, function (Service $a, Service $b) {
|
||||||
@@ -144,7 +145,7 @@ class Travel
|
|||||||
* Maps selection group IDs to their corresponding services based on
|
* Maps selection group IDs to their corresponding services based on
|
||||||
* the predefined included services mapping.
|
* the predefined included services mapping.
|
||||||
*
|
*
|
||||||
* @return array The included services from selection groups
|
* @return array<int, Service> The included services from selection groups
|
||||||
*/
|
*/
|
||||||
public function getIncludedServices(): array
|
public function getIncludedServices(): array
|
||||||
{
|
{
|
||||||
@@ -168,7 +169,7 @@ class Travel
|
|||||||
*
|
*
|
||||||
* @param array<int> $ids The array of room IDs to filter by
|
* @param array<int> $ids The array of room IDs to filter by
|
||||||
*
|
*
|
||||||
* @return array<Room> The filtered rooms array
|
* @return array<int, Room> The filtered rooms array
|
||||||
*/
|
*/
|
||||||
public function getRoomsByIds(array $ids): array
|
public function getRoomsByIds(array $ids): array
|
||||||
{
|
{
|
||||||
@@ -198,6 +199,7 @@ class Travel
|
|||||||
$result[$room->id] = $room;
|
$result[$room->id] = $room;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -163,7 +163,7 @@ class BookingCreateParticipantType extends AbstractType
|
|||||||
*/
|
*/
|
||||||
private function addDynamicFields(FormInterface $form, BookingDtoInterface $bookingDto, int $participantIndex): void
|
private function addDynamicFields(FormInterface $form, BookingDtoInterface $bookingDto, int $participantIndex): void
|
||||||
{
|
{
|
||||||
$dynamicFields = ['assignedRoomId']; // List of fields that need dynamic configuration
|
$dynamicFields = ['assignedRoomId', 'courses']; // List of fields that need dynamic configuration
|
||||||
|
|
||||||
foreach ($dynamicFields as $fieldName) {
|
foreach ($dynamicFields as $fieldName) {
|
||||||
if ($this->fieldOptionsProvider->hasFieldOptions($fieldName)) {
|
if ($this->fieldOptionsProvider->hasFieldOptions($fieldName)) {
|
||||||
|
|||||||
@@ -17,7 +17,8 @@ class BookingEditType extends AbstractType
|
|||||||
{
|
{
|
||||||
public function __construct(
|
public function __construct(
|
||||||
private readonly ParticipantFieldHandlerRegistry $participantFieldHandlerRegistry,
|
private readonly ParticipantFieldHandlerRegistry $participantFieldHandlerRegistry,
|
||||||
) {}
|
) {
|
||||||
|
}
|
||||||
|
|
||||||
public function buildForm(FormBuilderInterface $builder, array $options): void
|
public function buildForm(FormBuilderInterface $builder, array $options): void
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -78,7 +78,7 @@ abstract class AbstractFieldOptionsProvider implements FieldOptionsProviderInter
|
|||||||
* Symfony form field options.
|
* Symfony form field options.
|
||||||
*
|
*
|
||||||
* Example implementation:
|
* Example implementation:
|
||||||
*
|
*
|
||||||
* protected function registerFieldOptionProviders(): void
|
* protected function registerFieldOptionProviders(): void
|
||||||
* {
|
* {
|
||||||
* $this->fieldOptionProviders['fieldName'] = fn($bookingDto, $participantIndex) => [
|
* $this->fieldOptionProviders['fieldName'] = fn($bookingDto, $participantIndex) => [
|
||||||
@@ -88,4 +88,4 @@ abstract class AbstractFieldOptionsProvider implements FieldOptionsProviderInter
|
|||||||
* }
|
* }
|
||||||
*/
|
*/
|
||||||
abstract protected function registerFieldOptionProviders(): void;
|
abstract protected function registerFieldOptionProviders(): void;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ declare(strict_types=1);
|
|||||||
|
|
||||||
namespace App\Form\Service;
|
namespace App\Form\Service;
|
||||||
|
|
||||||
|
use App\BusProNet\Constants;
|
||||||
|
use App\BusProNet\Model\Service;
|
||||||
use App\Form\Model\BookingCreateDto;
|
use App\Form\Model\BookingCreateDto;
|
||||||
use App\Form\Model\BookingDtoInterface;
|
use App\Form\Model\BookingDtoInterface;
|
||||||
use App\Form\Service\Abstract\AbstractFieldOptionsProvider;
|
use App\Form\Service\Abstract\AbstractFieldOptionsProvider;
|
||||||
@@ -84,6 +86,23 @@ class ParticipantFieldOptionsProvider extends AbstractFieldOptionsProvider
|
|||||||
: null,
|
: null,
|
||||||
];
|
];
|
||||||
|
|
||||||
|
// Courses field provider - provides available courses from travel data
|
||||||
|
$this->fieldOptionProviders['courses'] = fn (BookingDtoInterface $bookingDto) => [
|
||||||
|
'label' => 'Kurse',
|
||||||
|
'multiple' => true,
|
||||||
|
'expanded' => true,
|
||||||
|
'required' => false,
|
||||||
|
'choices' => array_reduce(
|
||||||
|
$bookingDto->travel->getAdditionalServicesByGroup(Constants::TOKEN_COURSES),
|
||||||
|
function (array $choices, Service $service) {
|
||||||
|
$choices[$service->label] = $service->id;
|
||||||
|
|
||||||
|
return $choices;
|
||||||
|
},
|
||||||
|
[]
|
||||||
|
),
|
||||||
|
];
|
||||||
|
|
||||||
// Future field providers would be added here, for example:
|
// Future field providers would be added here, for example:
|
||||||
//
|
//
|
||||||
// $this->fieldOptionProviders['mealPreference'] = fn($bookingDto, $participantIndex) => [
|
// $this->fieldOptionProviders['mealPreference'] = fn($bookingDto, $participantIndex) => [
|
||||||
|
|||||||
@@ -40,7 +40,7 @@
|
|||||||
{{ form_row(participant.bodyDimensions.shoeSize) }}
|
{{ form_row(participant.bodyDimensions.shoeSize) }}
|
||||||
{{ form_row(participant.bodyDimensions.weight) }}
|
{{ form_row(participant.bodyDimensions.weight) }}
|
||||||
</div>
|
</div>
|
||||||
<div class="grid grid-cols-1 gap-4 pt-4">
|
<div class="grid grid-cols-1 gap-4">
|
||||||
{# hx-swap="none" tells HTMX not to do a normal swap, as OOB will handle it #}
|
{# hx-swap="none" tells HTMX not to do a normal swap, as OOB will handle it #}
|
||||||
{{ form_row(participant.assignedRoomId, {
|
{{ form_row(participant.assignedRoomId, {
|
||||||
'attr': {
|
'attr': {
|
||||||
@@ -49,6 +49,11 @@
|
|||||||
}
|
}
|
||||||
}) }}
|
}) }}
|
||||||
</div>
|
</div>
|
||||||
|
<div class="grid grid-cols-2 gap-4">
|
||||||
|
{% if participant.courses is defined %}
|
||||||
|
{{ form_row(participant.courses) }}
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</fieldset>
|
</fieldset>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user