6

I want to reuse some forms in my component. The subform field does the job. However, I need to remove some fields and/or field groups when displaying the subform.

I tried to use the JForm methods removeGroup() and removeField() but it won't remove them from the subform.

I guess that a new layout is the way to go. I could specify the layout in the field instead of layout='joomla.form.field.subform.default'.
Would this work?

If so, how do I implement the custom layout?
Examples would be very much appreciated.

2 Answers 2

4

Edited to add subform field type-specific answer:

Having looked at it properly, attaching your own layout to the subform field type is super-easy.

Create a layouts folder in the same parent component folder (site or admin) as the XML file, and put your layout in it:

-com_myComponent 
    - controllers
    - layouts
        - mylayout.php
    - models
        - forms

Add layout="mylayout" to your subform field in your XML and there you go.

Can't get much easier!

Should also note your layout file names can be the same as the default ones, yours will always get loaded if there's any conflict. So, for example, even though there's a subform layout called default.php you can still name yours default.php and it'll work fine.

Pre-edit answer:

Here's an example of how to include a layout from one of mine:

<?php echo JLayoutHelper::render('layouts.dupebutton', $dupeData, JPATH_COMPONENT_ADMINISTRATOR); ?>
  • First argument is 'layoutFolder.layoutName'.
  • Second argument is the data to pass to the layout (you'll be passing your form/fields).
  • Third is the base path to use to search for the layout folder/file (in this case the path to the admin install of my component).

You need to add something similar to that when you want your layout to be rendered.

My com_myComponent folder in Joomla's administrator folder (ie. JPATH_COMPONENT_ADMINISTRATOR) has this structure:

-com_myComponent 
    - classes
    - controllers
    - layouts
        - dupebutton.php
        - anotherlayout.php

Joomla's layout helper will pass the data you specified to the layout when it renders it. When the layout is rendered it will contain a pre-assigned variable called $displayData. You can just use this variable as is, but it seems to be Joomla convention to add this line in the <?php tags at the top of your layout files:

$data = $displayData;

Now it's just a case of building the layout using the form fields you want. Let me know if you also want examples of that, but it sounds like you know how already.

Incidentally, I'm pretty sure it is actually possible to select from form subgroups, but the syntax isn't very intuitive or well documented - last time I tried to do it I gave up much like you are now.

There are also multiple ways to achieve what you want, there are alternatives to using a layout. Still, it's as good a solution as any, so I'd stick with it.

4
  • Thank you for the reply. I've not used layouts before so the information is very helpful. The subform field has a layout parameter with dot-notation to the layout file. Three standard layouts are defined for now. I was thinking that I could just use my own layout in place of one of those. But, perhaps not. I've glanced at the subform field code but I don't see on quick inspection how they're rendering the layouts. I'll try your approach and see what happens.
    – nimble
    Nov 21, 2016 at 21:01
  • That would involve overriding Joomla core. Don't do that. Subform field type is brand new, just having a look at it now, but you should easily be able to change the default layout to own of your own. It's just a matter of working out how the dot notation works - docs are a bit lacking (aren't they always?), so I'm looking through the code.
    – Bathmat
    Nov 22, 2016 at 0:09
  • Answer updated mate.
    – Bathmat
    Nov 22, 2016 at 1:07
  • Thanks for the help. I put more due diligence into reverse engineering the code and came up with the answer. It's as simple as I had hoped.
    – nimble
    Nov 22, 2016 at 16:03
2

To place a subform (Joomla! 3.6+) within another "master" form and use a custom layout:

1) In the master JForm XML file use the subform field type.

<field name= "fieldname"
    description= "Field name description"
    type= "subform"
    label= "Field Label"
    required= "true"
    formsource= "/administrator/components/com_mycomponent/models/forms/myform.xml"
    layout="myfolder.mylayoutfile"
/>

formsource is the path to the JForm XML subform to be rendered.

layout is the dot-notation path to the custom layout file. You must have a "layouts" folder in your component's directory structure. So, it would be com_mycomponent/layouts. Under the layouts folder you can create other folders (if you wish). In the example above, "myfolder" is a folder under "layouts" and "mylayoutfile" is the custom PHP layout file in that folder. Don't specify "layouts" in the dot-notation path and do not add .php to the filename.

2) This is an example layout PHP file that can be modified for your purposes.

<?php
defined('_JEXEC') or die;
extract($displayData);

$form = $forms[0];
?>

<div class="subform-wrapper">
    <?php foreach($form->getGroup('') as $field): ?>
        <?php echo $field->renderField(); ?>
    <?php endforeach; ?>
</div>

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.