-
Notifications
You must be signed in to change notification settings - Fork 47
/
82_DynamicChoice.md
131 lines (107 loc) · 3.91 KB
/
82_DynamicChoice.md
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
# Dynamic Choice
The Dynamic Choice Type allows to generate Drop-Down / Checkbox / Radio Elements with dynamic content. For Example a Product List.
## Usage
In the FormBuilder Backend add a "Dynamic Choice Type" Field. There you'll find a "Service Name" Field with the defined Services.
In the next Section you'll learn how to add such services.
## Error Handling
**Important**: It's not possible to add custom validation messages within the DynamicChoice Service.
That's because you're dealing with a already rendered form type (dynamic choice).
To add some validations you could use the default constraints in the form builder itself or
by extending the default options via [form extensions](http://symfony.com/doc/current/form/create_form_type_extension.html).
## Add Service
```yaml
App\Services\FormBuilderBundle\ProductChoices:
autowire: true
public: false
tags:
- { name: form_builder.dynamic_choice_builder, label: 'Product Selector' }
```
## PHP Service (Simple)
```php
<?php
namespace App\Services\FormBuilderBundle;
use FormBuilderBundle\Form\ChoiceBuilderInterface;
use Symfony\Component\Form\CallbackTransformer;
use Symfony\Component\Form\FormBuilderInterface;
use App\Model\Product;
class ProductChoices implements ChoiceBuilderInterface
{
protected $builder;
public function setFormBuilder(FormBuilderInterface $builder)
{
$this->builder = $builder;
// transform data back to string (to display the product name in the email for example)
$builder->addModelTransformer(new CallbackTransformer(
function ($entries) {
return $entries;
},
function ($entries) {
if (empty($entries)) {
return $entries;
}
if (is_array($entries)) {
$data = [];
foreach ($entries as $id) {
$product = Product::getById($id);
$data[] = $product->getName();
}
return implode(', ', $data);
} else {
$product = Product::getById($entries);
return $product->getName();
}
}
));
}
public function getList()
{
$product1 = Product::getById(89);
$product2 = Product::getById(47);
return [
$product1->getName() => $product1->getId(),
$product2->getName() => $product2->getId()
];
}
}
```
## PHP Service (Advanced)
You could implement the `AdvancedChoiceBuilderInterface` to get more control about your choice element:
```php
<?php
namespace App\Services\FormBuilderBundle;
use FormBuilderBundle\Form\AdvancedChoiceBuilderInterface;
use Symfony\Component\Form\FormBuilderInterface;
use App\Model\Product;
class ProductChoices implements AdvancedChoiceBuilderInterface
{
protected $builder;
public function setFormBuilder(FormBuilderInterface $builder)
{
// same as in simple service
}
public function getList()
{
// same as in simple service
}
public function getChoiceValue($element = null)
{
// @see: https://symfony.com/doc/current/reference/forms/types/choice.html#choice-value
}
public function getChoiceLabel($element, $key, $index)
{
// @see: https://symfony.com/doc/current/reference/forms/types/choice.html#choice-label
}
public function getChoiceAttributes($element, $key, $index)
{
// @see: https://symfony.com/doc/current/reference/forms/types/choice.html#choice-attr
}
public function getGroupBy($element, $key, $index)
{
// @see: https://symfony.com/doc/current/reference/forms/types/choice.html#group-by
}
public function getPreferredChoices($element, $key, $index)
{
// @see: https://symfony.com/doc/current/reference/forms/types/choice.html#preferred-choices
}
}
```