Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

When add()/init() is called right after the object is created it should have no effect on the result. #1027

Open
mvorisek opened this issue Mar 29, 2020 · 15 comments
Assignees

Comments

@mvorisek
Copy link
Member

mvorisek commented Mar 29, 2020

Example:

$form = \atk4\ui\Form::addTo($personModal, ['segment']);
$personDropDown = \atk4\ui\FormField\DropDown::addTo($form);

// move submit button to the end of the form
$form->layout->removeElement(array_search($form->buttonSave, $form->layout->elements, true));
$form->layout->add($form->buttonSave);
  • Why is the save button (added in init, ie. before the dropdown is added initially) not moved to the end with the code above?

  • What is currently the best way to do so once the layout is initialized?

  • Currently Form supports AboveFields region. Wdyt to introduce region like afterInit for all elements that add some elements the the layout?

@DarkSide666
Copy link
Member

Currently the only way to change order of elements after they are added is to mess with elements array of parent (or remove element and add it at the end) I think. At least that's what I have also done in some places.
Probably there should be some nice-named method for that.

@ibelar
Copy link
Contributor

ibelar commented Mar 30, 2020

Form rely on a layout View to add field and buttons. This layout view is added to the form template inside the Content tag.

In your code above, when creating the form instance, initLayout method is called, thus inserting the layout view within the Content region of the form.
Then, your code added the $dropdown field within the same Content region of the form template.

Since the save button is part of the layout view, not the form view, and that it was added to the form template Content region first, then the button will always render first.

Hope this help.

@mvorisek
Copy link
Member Author

@ibelar Thank you - yes, the issue with my example is that I added Dropdown to Form but the button is added to a layout... This moved the button to the end:

$form->removeElement(array_search($form->layout, $form->elements, true));
$form->add($form->layout);

But when I changed the second line of the original example to add the Dropdown to layout like:

$personDropDown = \atk4\ui\FormField\DropDown::addTo($form->layout);

Then I received an Exception:

Error: Call to a member function getCaption() on null (in .../vendor/atk4/ui/src/FormLayout/Generic.php:164)

Is this a bug? I am using this for one use case where I do not need model, thus I do not / can not easily use Form->addField().

@ibelar
Copy link
Contributor

ibelar commented Mar 30, 2020

@mvorisek - no - this is not a bug. When rendering the form layout, it see that the object is a field type and try to set caption on it.

Not sure what you are trying to do but if you do not meed model, then why not just use form without model?

$form = \atk4\ui\Form::addTo($personModal, ['segment']);
$personDropDown = $form->addField('person', ['DropDown']);

@mvorisek
Copy link
Member Author

mvorisek commented Mar 30, 2020

I need a html form and single dropdown element with save button. Nothing else.

This works:

$personDropDown = new \atk4\ui\FormField\DropDown();
$form->addField('x', $personDropDown);

image

but the Field name (x in this example) is rendered.

To sum it up - I understand the logic, initially I tried to reorder elements in $form instead of $form->layout by a mistake. The order is given by the order of elements.

Currently Form supports AboveFields region. Wdyt to introduce region like afterInit for all elements that add some elements the the layout?

I am still thinking calling add() / init() should have optimally zero impact on the result. With the new ::addTo() method, which is used to create an object instance and to add it to the parent immediatelly, this is important. I am assigning this under myself and I will propose a PR for it.

Then reordering should not be needed that much thus renamed the title of this issue.

@mvorisek mvorisek removed the question label Mar 30, 2020
@mvorisek mvorisek changed the title How to reorder elements in the layout? When add()/init() is called right after the object is created it should have no effect on the result. Mar 30, 2020
@PhilippGrashoff
Copy link
Collaborator

PhilippGrashoff commented Mar 30, 2020

Hi, if you want to hide the fields caption (in your case the X), you can use the parameter inline of a FormLayout, e.g. $form->layout->inline = true. This, IIRC, leads to only the fields being rendered without the labels.

@mvorisek
Copy link
Member Author

mvorisek commented Mar 30, 2020

@PhilippGrashoff Thanks for pointing it out! It does not solve the that the result after add() / init() is different, but the labels are gone:
image

But the property name inline is very confusing - @PhilippGrashoff, time to rename to noLabels?

@PhilippGrashoff
Copy link
Collaborator

I agree its confusing. More confusing even when regarding that Fomantic UI means by "inline" that the label is left of the input instead of above:
https://fomantic-ui.com/collections/form.html#inline-field

@ibelar you are our form master. What do you think?

@romaninsh
Copy link
Member

Form layout is a custom view that relies on fields getInput and augments it with labels, captions etc. There is a class for a form without any layout engine or you can use custom form layout.

@ibelar
Copy link
Contributor

ibelar commented Mar 31, 2020

@PhilippGrashoff - I believe class inline in Fomantic-UI is meant to be applied on a group of fields. Having the first field in the group to have its label set to the left of it and the remaining fields in the group to appear next to each other.

@mvorisek
Copy link
Member Author

mvorisek commented Mar 31, 2020

@PhilippGrashoff - I believe class inline in Fomantic-UI is meant to be applied on a group of fields. Having the first field in the group to have its label set to the left of it and the remaining fields in the group to appear next to each other.

@ibelar But in atk the inline is used for noLabels :), see #1027 (comment) , time to change it?

@georgehristov
Copy link
Collaborator

Wdyt to introduce region like afterInit for all elements that add some elements the the layout?

We were discussing introducing hooks into the init method for this purpose as some operations in init can only be performed when all elements added.

@ibelar
Copy link
Contributor

ibelar commented Mar 31, 2020

@mvorisek - sorry was not clear enough. It also has the same behavior for atk4/ui. Declaring 'inline' field does remove the label because it follow Fomantic-UI rule. See demos/form.php in Layout Control tab

$gr = $f->addGroup(['Name', 'inline' => true]);
$gr->addField('first_name', ['width' => 'eight']);
$gr->addField('middle_name', ['width' => 'three', 'disabled' => true]);
$gr->addField('last_name', ['width' => 'five']);

Screen Shot 2020-03-31 at 10 22 55 AM

@mvorisek
Copy link
Member Author

mvorisek commented Mar 31, 2020

@ibelar Ok, thanks for the demo, in atk, "noLabels" is only side effect of inline.

@PhilippGrashoff
Copy link
Collaborator

well, "inline" class in Fomatic-UI can be used two ways, at least 2 I know of:

  1. On a single field. <div class="inline field"> Causes the label to be left of the input instead of above, as FUI docs state.
  2. In a group of fields, so far I used <div class="inline fields"><div class="field">...</div><div class="field">...</div></div> This also leads to all labels to appear left of the input instead of below. None of the FUI uses of "inline" class removes the labels...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

6 participants