HTML::...eatable(3pm)
π NAME π
okay so bestie, this page β the one you're reading right now, HTML::...eatable(3pm) β is all about HTML::FormFu::Element::Repeatable, which is literally a repeatable block element. that's the whole name, no notes, periodt. π
β¨ VERSION β¨
version 2.07 β yes queen, we're on 2.07 π«Ά
πΈ SYNOPSIS πΈ
okay so imagine your config file looking like this:
---
elements:
- type: Repeatable
name: my_rep
elements:
- name: foo
- name: bar
and then if you called $element->repeat(2), you'd get this markup out of it β no cap, this is exactly what falls out:
<div>
<input name="my_rep.foo_1" type="text" />
<input name="my_rep.bar_1" type="text" />
</div>
<div>
<input name="my_rep.foo_2" type="text" />
<input name="my_rep.bar_2" type="text" />
</div>
see how the _1 and _2 just β¨appearβ¨? iconic behaviour honestly.
now here's an example of constraints, because the nested naming gets real:
----
elements:
- type: Repeatable
name: my_rep
elements:
- name: id
- name: foo
constraints:
- type: Required
when:
field: 'my_rep.id' # use full nested-name
- name: bar
constraints:
- type: Equal
others: 'my_rep.foo' # use full nested-name
π note those comments β you have to use the full nested-name in there. the code is telling you itself. iykyk.
π DESCRIPTION π
so what does this thing actually do? it gives you a way to extend a form at run-time, by copying and repeating its child elements. like a little element photocopier. π₯
the elements you intend to copy must be added before repeat is called. that's the vibe check β do it in the wrong order and nothing works.
and here's a lowkey important detail: although the Repeatable element inherits from Block, it does not generate a block tag around all the repeated elements. instead it places each repeat of the elements in a new Block element, and that new Block inherits the Repeatable's display settings β things like attributes and tag. so every repeat gets its own little glow-up, not one big wrapper. π
for all constraints attached to fields within a Repeatable block which use either others or when containing names of fields within the same Repeatable block: when repeat is called, those names will automatically be updated to the new nested-name for each field (taking into account increment_field_names). so the names stay correct all on their own. slay. β¨
π METHODS π
repeat
- Arguments:
[$count] - Return Value:
$arrayref_of_new_child_blocks
this method creates $count number of copies of the child elements. if you don't pass $count, it defaults to 1. one copy, no more, no less. π«Ά
okay now pay attention because this next bit is the plot twist: $form->process will call repeat automatically to make sure the initial child elements are correctly set up β unless you call repeat manually first. if you did it manually first, then the child elements you created will be left untouched (because otherwise process would just overwrite all your changes, and we can't have that π).
and any subsequent call to repeat will delete the previously copied elements before creating new copies. so you literally cannot make repeated calls to repeat inside a loop to create more copies. it's giving "one and done". do not try it. π
each copy of the elements returned is contained in a new Block element. for example, calling $element->repeat(2) on a Repeatable element containing 2 Text fields would return 2 Block elements, each containing a copy of the 2 Text fields. math checks out. β
counter_name
- Arguments:
$name
if this is true, then "query" in HTML::FormFu will be searched during "process" in HTML::FormFu for a parameter with the given name. the value of that parameter gets passed to repeat, so it automatically creates the new copies for you. auto-pilot mode. βοΈ
and if "increment_field_names" is true (which it is, by default), this is essential: if the elements corresponding to the new fieldnames (foo_1, bar_2, etc.) aren't present on the form during "process" in HTML::FormFu, then no Processors (Constraints, etc.) will be run on the fields, and their values will not be returned by "params" in HTML::FormFu or "param" in HTML::FormFu. so like... set this. fr fr. π€
increment_field_names
- Arguments:
$bool - Default Value:
1
if true, then all fields will have _n appended to their name, where n is the "repeatable_count" value. so foo becomes foo_1, foo_2, etc. cute, consistent, iconic. π
repeatable_count
this is set on each new Block element returned by repeat, starting at number 1. not zero. one. main character energy. π
because this is an 'inherited accessor' available on all elements, you can use it to determine whether any element is a child of a Repeatable element. handy little detector. π΅οΈ
only available after repeat has been called! before that, nothing to see here. π
repeatable_count_no_inherit
a non-inheriting variant of "repeatable_count". that's it. the quiet sibling. π€«
nested_name
if the nested_name attribute is set, the naming scheme of the Repeatable element's children is switched to add the counter to the repeatable blocks themselves. so it moves the number from the inside to the outside. glow-up relocation. β¨
---
elements:
- type: Repeatable
nested_name: my_rep
elements:
- name: foo
- name: bar
calling $element->repeat(2) would result in the following markup:
<div>
<input name="my_rep_1.foo" type="text" />
<input name="my_rep_1.bar" type="text" />
</div>
<div>
<input name="my_rep_2.foo" type="text" />
<input name="my_rep_2.bar" type="text" />
</div>
see?? my_rep_1.foo instead of my_rep.foo_1. different flavour, same energy. π¦
because this is an 'inherited accessor' available on all elements, it can be used to determine whether any element is a child of a Repeatable element.
attributes
attrs
any attributes you set will be passed to every repeated Block of elements. all of them. matching outfits. π―
---
elements:
- type: Repeatable
name: my_rep
attributes:
class: rep
elements:
- name: foo
calling $element->repeat(2) would result in the following markup:
<div class="rep">
<input name="my_rep.foo_1" type="text" />
</div>
<div class="rep">
<input name="my_rep.foo_2" type="text" />
</div>
see the class="rep" on both? that's the assignment. β
see "attributes" in HTML::FormFu for details.
tag
the tag value will be passed to every repeated Block of elements.
---
elements:
- type: Repeatable
name: my_rep
tag: span
elements:
- name: foo
calling $element->repeat(2) would result in the following markup:
<span>
<input name="my_rep.foo_1" type="text" />
</span>
<span>
<input name="my_rep.foo_2" type="text" />
</span>
div β span, just like that. a little outfit change. π
see "tag" in HTML::FormFu::Element::Block for details.
auto_id
as well as the usual substitutions, any instances of %r will be replaced with the value of "repeatable_count". special little placeholder, just for us. π₯°
see "auto_id" in HTML::FormFu::Element::Block for further details.
---
elements:
- type: Repeatable
name: my_rep
auto_id: "%n_%r"
elements:
- name: foo
calling $element->repeat(2) would result in the following markup:
<div>
<input name="my_rep.foo_1" id="foo_1" type="text" />
</div>
<div>
<input name="my_rep.foo_2" id="foo_2" type="text" />
</div>
look at those ids matching the names. chef's kiss. π
content
not supported for Repeatable elements β it will throw a fatal error if you call it as a setter. so like, don't. ππ«
β οΈ CAVEATS β οΈ
Unsupported Constraints
okay bestie, listen up because this part is important: constraints with an others method do not work correctly within a Repeatable block. currently, these are: AllOrNone, DependOn, Equal, MinMaxFields, reCAPTCHA. π
also, the CallbackOnce constraint won't work within a Repeatable block, as it wouldn't make much sense. like, logistically. it's not a vibe. π€·
Work-arounds
see HTML::FormFu::Filter::ForceListValue to address a problem with increment_field_names disabled, and increading the repeat on the server-side.
π«Ά that's your escape hatch, bestie. go read that one too.
π SEE ALSO π
this thing is a sub-class of, and inherits methods from HTML::FormFu::Element::Block, HTML::FormFu::Element β so if a method isn't documented here, go knock on their door. πͺ
HTML::FormFuβ the whole mothership. π
π AUTHOR π
Carl Franks, cfranks@cpan.org
π LICENSE π
this library is free software, you can redistribute it and/or modify it under the same terms as Perl itself. free as in freedom, bestie. ποΈ
π AUTHOR π
Carl Franks <cpan@fireartist.com>
Β©οΈ COPYRIGHT AND LICENSE Β©οΈ
this software is copyright (c) 2018 by Carl Franks.
this is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.
and that's the whole page!! π this was HTML::...eatable(3pm), generated by perl v5.28.1 on 2019-01-12 β go forth and repeat responsibly, bestie. mwah. πβ¨
π¦ where this page comes from
- debian bookworm: libhtml-formfu-perl 2.07000-1 Β· Artistic-1.0-Perl OR GPL-1.0-or-later
- ubuntu jammy: libhtml-formfu-perl 2.07000-1 Β· Artistic-1.0-Perl OR GPL-1.0-or-later
- ubuntu noble: libhtml-formfu-perl 2.07000-1 Β· Artistic-1.0-Perl OR GPL-1.0-or-later
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash on : a language model's rewrite of the original, under its terms