ParameterFieldBuilder
in package
uses
ParameterFieldsTrait, GroupsTrait, RulesTrait, DefaultsTrait, DependentSelectTrait
Stateless builder of dynamic parameter fields into a given form.
It lets an ordinary admin presenter form (createForm()) build parameter fields, not only a
standalone component. A consumer:
- calls init() with the resolved items, groups and context (and mode),
- calls build() to insert fields, dependent selects, rules and groups into the form,
- calls applyEntityDefaults() to prefill from the entity (edit),
- after submit calls extractValues() to get the persistable values for saving.
The AJAX dependent-select signal is handled by the hosting UI control (presenter/component)
through Coolsoftcz\DependentSelectBox\DependentSelectBoxAware; the builder only calls the
global Form::addDependentSelectBox() (registered via FormExtension).
Shared by front end and admin. Type handlers live in ParameterHandlerRegistry.
Table of Contents
Properties
- $context : ParameterFormContext
- $entityValues : array<int, mixed>
- $itemsByGroups : array<int, array<int, ParameterFormItem>>
- $mode : string
- $onlyDefaultParameters : bool
- $parameterGroupList : array<int, ParameterGroupInterface>
- $parameterItems : array<int, ParameterFormItem>
- $registry : ParameterHandlerRegistry
Methods
- __construct() : mixed
- applyEntityDefaults() : void
- Prefills the fields with entity values (see {@see setEntityValues()}); call it after {@see build()}.
- applyEntityDefaultsForNewFields() : void
- Prefills from the entity only the fields that are not in the submitted POST, i.e. fields newly revealed by a category choice on an AJAX signal (`parametersRefresh`, row removal).
- build() : void
- Inserts the parameter fields (plus dependent selects, rules and groups) into the form.
- extractValues() : array<int, array<int, array{value: mixed, value2?: ?string}>>
- Returns the persistable values of the submitted form (not file/image types).
- findParameterByKey() : ParameterInterface|null
- getFormKey() : string
- Returns the form control key of the parameter (`parameter_<id>`), used to denormalize a parameter value into a column.
- getParameterItems() : array<int, ParameterFormItem>
- getUploaderParameterIds() : array<string|int, int>
- Returns ids of parameters with a dropzone uploader (`IMAGE_UPLOADER`, `FILE_UPLOADER`).
- init() : void
- setEntityValues() : void
- parameterKey() : string
- addParameterControlsToGroup() : void
- Adds the parameter control(s) to the group.
- addParameterFields() : void
- applyConditionsToElement() : void
- applyDefaults() : void
- Prefills the form from a map of values supplied by the child component (e.g. from the `Advert` entity via ParameterRels).
- areAllConditionsMet() : bool
- buildDependentData() : DependentData
- collectOptionLabels() : array<int, string>
- collectRuleControlledOptionIds() : array<int, true>
- collectShowSelectOptionsRules() : array<string|int, ParameterRuleInterface>
- collectSourceKeys() : array<string|int, string>
- controlHasItem() : bool
- Returns whether the select control has the given option among its items.
- extractConditionValues() : array{0: int[], 1: string[]}
- extractParameterIdFromKey() : int|null
- getEntityValues() : array<int, mixed>
- Hook for `DependentSelectTrait`: the initial parent values of the dependent selects.
- getMode() : string
- getParameterGroupLabel() : string
- getParameterTranslation() : ParameterTextInterface|null
- indexById() : array<int, T>
- indexItemsByGroups() : void
- indexItemsById() : array<int, ParameterFormItem>
- initializeBlacklistedWordRules() : void
- initializeFormElementDependencies() : void
- initializeFormRules() : void
- initializeLengthRules() : void
- Upper limit of text values from the parameter `max_length` (admin › Parameters, "Max. number of characters").
- initializeRequiredRules() : void
- initializeToggleRules() : void
- initializeUrlRules() : void
- insertFormElementsIntoGroups() : void
- isConditionMet() : bool
- isFieldSubmitted() : bool
- Returns whether the parameter field is present in the submitted POST.
- replaceWithDependentSelect() : void
- resolveDefaultValue() : string|null
- resolveInitialParentValues() : array<string, mixed>
- resolveOptionLabel() : string
- resolveType() : int|null
- sanitizeParameterValue() : string
- sanitizeRows() : array<int, array{value: mixed, value2?: ?string}>
- Applies the parameter content filters to the extracted rows (`value` only, not `value2`); form mode only.
- setRequiredForParameter() : void
- setRequiredForParametersInGroup() : void
- setRequiredForTargets() : void
- Sets the required flag for the targets.
Properties
$context
private
ParameterFormContext
$context
$entityValues
private
array<int, mixed>
$entityValues
= []
parameterId => value | value[] (prefill from the entity)
$itemsByGroups
private
array<int, array<int, ParameterFormItem>>
$itemsByGroups
= []
items by resolved groupId
$mode
private
string
$mode
= \App\Core\Form\ParameterFormContext::MODE_FORM
$onlyDefaultParameters
private
bool
$onlyDefaultParameters
= false
$parameterGroupList
private
array<int, ParameterGroupInterface>
$parameterGroupList
= []
groups by id
$parameterItems
private
array<int, ParameterFormItem>
$parameterItems
= []
items by parameterId (source of the resolved order/required/groupId)
$registry read-only
private
ParameterHandlerRegistry
$registry
Methods
__construct()
public
__construct(ParameterHandlerRegistry $registry) : mixed
Parameters
- $registry : ParameterHandlerRegistry
applyEntityDefaults()
Prefills the fields with entity values (see {@see setEntityValues()}); call it after {@see build()}.
public
applyEntityDefaults(Form $form) : void
Parameters
- $form : Form
applyEntityDefaultsForNewFields()
Prefills from the entity only the fields that are not in the submitted POST, i.e. fields newly revealed by a category choice on an AJAX signal (`parametersRefresh`, row removal).
public
applyEntityDefaultsForNewFields(Form $form, array<string, mixed> $rawPost) : void
Uses setValue() (force) because setDefaultValue() is a no-op on a submitted form. Fields that
were submitted keep the value the user is typing. IMPORTANT: call it from the onClick redraw
callback (it runs after the eager loadHttpData, so setValue() wins), not on GET, where
applyEntityDefaults() runs.
Parameters
- $form : Form
- $rawPost : array<string, mixed>
-
raw POST (form control keys)
build()
Inserts the parameter fields (plus dependent selects, rules and groups) into the form.
public
build(Form $form) : void
Groups are added last; the consumer may add its own groups before or after.
Parameters
- $form : Form
extractValues()
Returns the persistable values of the submitted form (not file/image types).
public
extractValues(ArrayHash $values) : array<int, array<int, array{value: mixed, value2?: ?string}>>
The key is the parameterId, the value the rows to store (the handler decides scalar, multi or range).
Parameters
- $values : ArrayHash
Return values
array<int, array<int, array{value: mixed, value2?: ?string}>>findParameterByKey()
public
findParameterByKey(string $key) : ParameterInterface|null
Parameters
- $key : string
Return values
ParameterInterface|nullgetFormKey()
Returns the form control key of the parameter (`parameter_<id>`), used to denormalize a parameter value into a column.
public
getFormKey(ParameterInterface $parameter) : string
Parameters
- $parameter : ParameterInterface
Return values
stringgetParameterItems()
public
getParameterItems() : array<int, ParameterFormItem>
Return values
array<int, ParameterFormItem>getUploaderParameterIds()
Returns ids of parameters with a dropzone uploader (`IMAGE_UPLOADER`, `FILE_UPLOADER`).
public
getUploaderParameterIds() : array<string|int, int>
The consumer builds the uploader child components and the form control to uploader map from them.
Return values
array<string|int, int>init()
public
init(array<string|int, ParameterFormItem> $parameterItems, array<string|int, ParameterGroupInterface> $parameterGroups, ParameterFormContext $context[, string $mode = ParameterFormContext::MODE_FORM ][, bool $onlyDefaultParameters = false ]) : void
Parameters
- $parameterItems : array<string|int, ParameterFormItem>
-
resolved items (source of truth for order/required/groupId)
- $parameterGroups : array<string|int, ParameterGroupInterface>
-
groups for the ids found in the items
- $context : ParameterFormContext
- $mode : string = ParameterFormContext::MODE_FORM
- $onlyDefaultParameters : bool = false
setEntityValues()
public
setEntityValues(array<int, mixed> $entityValues) : void
Parameters
- $entityValues : array<int, mixed>
-
parameterId => value | value[]
parameterKey()
protected
parameterKey(ParameterInterface $parameter) : string
Parameters
- $parameter : ParameterInterface
Return values
stringaddParameterControlsToGroup()
Adds the parameter control(s) to the group.
private
addParameterControlsToGroup(Form $form, ControlGroup $group, string $key) : void
Most types have one control at $key; multi-field types (range) have {key}_from and {key}_to.
Parameters
- $form : Form
- $group : ControlGroup
- $key : string
addParameterFields()
private
addParameterFields(Form $form) : void
Parameters
- $form : Form
applyConditionsToElement()
private
applyConditionsToElement(Form $form, ParameterInterface $parameter, ParameterRuleInterface $rule) : void
Parameters
- $form : Form
- $parameter : ParameterInterface
- $rule : ParameterRuleInterface
applyDefaults()
Prefills the form from a map of values supplied by the child component (e.g. from the `Advert` entity via ParameterRels).
private
applyDefaults(Form $form, array<int, mixed> $entityValues[, array<string, mixed>|null $skipSubmittedPost = null ]) : void
With $skipSubmittedPost === null it is a classic GET prefill (setDefaultValue()). With an
array it is force mode: setValue() fills only fields whose key is not in this POST, i.e. fields
newly revealed by an AJAX category refresh on a submitted form, where setDefaultValue() is a
no-op. Fields that are in the POST (the value the user is typing) are skipped so the database
value does not overwrite them.
Parameters
- $form : Form
- $entityValues : array<int, mixed>
-
parameterId => value | value[] - $skipSubmittedPost : array<string, mixed>|null = null
-
raw POST (form control keys) or null
areAllConditionsMet()
private
areAllConditionsMet(ParameterRuleInterface $rule, array<string, mixed> $parentValues) : bool
Parameters
- $rule : ParameterRuleInterface
- $parentValues : array<string, mixed>
Return values
boolbuildDependentData()
private
buildDependentData(ParameterInterface $parameter, array<string|int, ParameterRuleInterface> $rules, array<string, mixed> $parentValues, string|null $prompt) : DependentData
Parameters
- $parameter : ParameterInterface
- $rules : array<string|int, ParameterRuleInterface>
- $parentValues : array<string, mixed>
- $prompt : string|null
Return values
DependentDatacollectOptionLabels()
private
collectOptionLabels(ParameterInterface $parameter) : array<int, string>
Parameters
- $parameter : ParameterInterface
Return values
array<int, string>collectRuleControlledOptionIds()
private
collectRuleControlledOptionIds(array<string|int, ParameterRuleInterface> $rules) : array<int, true>
Parameters
- $rules : array<string|int, ParameterRuleInterface>
Return values
array<int, true>collectShowSelectOptionsRules()
private
collectShowSelectOptionsRules(ParameterInterface $parameter) : array<string|int, ParameterRuleInterface>
Parameters
- $parameter : ParameterInterface
Return values
array<string|int, ParameterRuleInterface>collectSourceKeys()
private
collectSourceKeys(Form $form, array<string|int, ParameterRuleInterface> $rules) : array<string|int, string>
Parameters
- $form : Form
- $rules : array<string|int, ParameterRuleInterface>
Return values
array<string|int, string> —form component keys (e.g. parameter_42)
controlHasItem()
Returns whether the select control has the given option among its items.
private
controlHasItem(BaseControl $element, int $id) : bool
Guards setDefaultValue() against a nonexistent or removed option. Select items are keyed by
option id (int); the string variant is checked too, for text keys.
Parameters
- $element : BaseControl
- $id : int
Return values
boolextractConditionValues()
private
extractConditionValues(ParameterRuleConditionInterface $condition) : array{0: int[], 1: string[]}
Parameters
- $condition : ParameterRuleConditionInterface
Return values
array{0: int[], 1: string[]}extractParameterIdFromKey()
private
extractParameterIdFromKey(string $controlKey) : int|null
Parameters
- $controlKey : string
Return values
int|nullgetEntityValues()
Hook for `DependentSelectTrait`: the initial parent values of the dependent selects.
private
getEntityValues() : array<int, mixed>
Return values
array<int, mixed>getMode()
private
getMode() : string
Return values
stringgetParameterGroupLabel()
private
getParameterGroupLabel(ParameterGroupInterface $parameterGroup) : string
Parameters
- $parameterGroup : ParameterGroupInterface
Return values
stringgetParameterTranslation()
private
getParameterTranslation(ParameterInterface $parameter) : ParameterTextInterface|null
Parameters
- $parameter : ParameterInterface
Return values
ParameterTextInterface|nullindexById()
private
indexById(array<string|int, T> $items) : array<int, T>
Parameters
- $items : array<string|int, T>
Tags
Return values
array<int, T>indexItemsByGroups()
private
indexItemsByGroups() : void
indexItemsById()
private
indexItemsById(array<string|int, ParameterFormItem> $items) : array<int, ParameterFormItem>
Parameters
- $items : array<string|int, ParameterFormItem>
Return values
array<int, ParameterFormItem>initializeBlacklistedWordRules()
private
initializeBlacklistedWordRules(Form $form) : void
Parameters
- $form : Form
initializeFormElementDependencies()
private
initializeFormElementDependencies(Form $form) : void
Parameters
- $form : Form
initializeFormRules()
private
initializeFormRules(Form $form) : void
Parameters
- $form : Form
initializeLengthRules()
Upper limit of text values from the parameter `max_length` (admin › Parameters, "Max. number of characters").
private
initializeLengthRules(Form $form) : void
Every value is stored in a text column of *_advert_parameter_rel, so without a limit 70,000 characters
failed the save on the database (strict mode) with the generic "could not be saved" message. A plain field
gets MAX_LENGTH (also the maxlength attribute); with the editor the visible text is counted
(EditorTextLength), not the HTML. data-char-counter switches on the counter at the field
(char-counter.js), which counts the same way.
Parameters
- $form : Form
initializeRequiredRules()
private
initializeRequiredRules(Form $form, array<string|int, ParameterRuleInterface> $rules) : void
Parameters
- $form : Form
- $rules : array<string|int, ParameterRuleInterface>
initializeToggleRules()
private
initializeToggleRules(Form $form, array<string|int, ParameterRuleInterface> $rules) : void
Parameters
- $form : Form
- $rules : array<string|int, ParameterRuleInterface>
initializeUrlRules()
private
initializeUrlRules(Form $form) : void
Parameters
- $form : Form
insertFormElementsIntoGroups()
private
insertFormElementsIntoGroups(Form $form) : void
Parameters
- $form : Form
isConditionMet()
private
isConditionMet(ParameterRuleConditionInterface $condition, array<string, mixed> $parentValues) : bool
Parameters
- $condition : ParameterRuleConditionInterface
- $parentValues : array<string, mixed>
Return values
boolisFieldSubmitted()
Returns whether the parameter field is present in the submitted POST.
private
isFieldSubmitted(array<string, mixed> $rawPost, string $key) : bool
It also considers handler sub-keys (range: {key}_from/{key}_to). An empty but submitted
text input (key='') counts as present, which respects a deliberate clearing by the user.
New fields (a new category) are not in the POST at all, so it returns false and they are
filled from the database.
Parameters
- $rawPost : array<string, mixed>
- $key : string
Return values
boolreplaceWithDependentSelect()
private
replaceWithDependentSelect(Form $form, ParameterInterface $parameter, string $key, array<string|int, ParameterRuleInterface> $rules, array<string|int, string> $sourceKeys, array<int, mixed> $entityValues) : void
Parameters
- $form : Form
- $parameter : ParameterInterface
- $key : string
- $rules : array<string|int, ParameterRuleInterface>
- $sourceKeys : array<string|int, string>
- $entityValues : array<int, mixed>
resolveDefaultValue()
private
resolveDefaultValue(ParameterInterface $parameter) : string|null
Parameters
- $parameter : ParameterInterface
Return values
string|nullresolveInitialParentValues()
private
resolveInitialParentValues(Form $form, array<string|int, string> $sourceKeys, array<int, mixed> $entityValues) : array<string, mixed>
Parameters
- $form : Form
- $sourceKeys : array<string|int, string>
- $entityValues : array<int, mixed>
Return values
array<string, mixed>resolveOptionLabel()
private
resolveOptionLabel(ParameterInterface $option) : string
Parameters
- $option : ParameterInterface
Return values
stringresolveType()
private
resolveType(ParameterInterface $parameter) : int|null
Parameters
- $parameter : ParameterInterface
Return values
int|nullsanitizeParameterValue()
private
sanitizeParameterValue(ParameterInterface $parameter, string $value) : string
Parameters
- $parameter : ParameterInterface
- $value : string
Return values
stringsanitizeRows()
Applies the parameter content filters to the extracted rows (`value` only, not `value2`); form mode only.
private
sanitizeRows(ParameterInterface $parameter, array<int, array{value: mixed, value2?: ?string}> $rows) : array<int, array{value: mixed, value2?: ?string}>
Parameters
- $parameter : ParameterInterface
- $rows : array<int, array{value: mixed, value2?: ?string}>
Return values
array<int, array{value: mixed, value2?: ?string}>setRequiredForParameter()
private
setRequiredForParameter(Form $form, int $parameterId, bool $required) : void
Parameters
- $form : Form
- $parameterId : int
- $required : bool
setRequiredForParametersInGroup()
private
setRequiredForParametersInGroup(Form $form, int $groupId, bool $required) : void
Parameters
- $form : Form
- $groupId : int
- $required : bool
setRequiredForTargets()
Sets the required flag for the targets.
private
setRequiredForTargets(Form $form, array<int|string, mixed> $targets, bool $required) : void
The items are ParameterRuleTargetInterface, but typed mixed: module entities return an
untyped Doctrine collection and the contract is enforced only by the instanceof below.
Parameters
- $form : Form
- $targets : array<int|string, mixed>
- $required : bool