Question

I've written a custom module which adds a new tab to admin category edit page, using UI component form ([Vendor] \ [Module]\view\adminhtml\ui_component\category_form.xml).

Everything works fine from textbox, text area to date field and even "insertListing".

But I have to add button as a field. When I took a look at

vendor/magento/module-ui/etc/ui_definition.xsd

I could see <xs:element type="button" name="button"/> as a formElement type.

But there are no reference in the core on how to use this button as a formElement in a UI component form.

Can someone throw some light on this? Thanks.

Was it helpful?

Solution

Okay I figured out a way to use a button element as a category attribute. What I've done is used the ElementTmpl property to render a category attribute as a Media browser.

Let's get into the code:

app/code/Vendor/Module/view/adminhtml/ui_component/category_form.xml

<field name="custom_attribute_code">
        <argument name="data" xsi:type="array">
        <item name="config" xsi:type="array">
            <item name="sortOrder" xsi:type="number">40</item>
            <item name="formElement" xsi:type="string">input</item>
            <!--<item name="notice" xsi:type="string">The categroy has to be saved after selecting an image</item>-->
            <item name="elementTmpl" xsi:type="string">Vendor_Module/form/element/custom-button</item>
            <item name="elementId" xsi:type="string">custom_attribute_code</item>
            <item name="dialogUrl" xsi:type="url" path="cms/wysiwyg_images/index">
                <param name="target_element_id">custom_attribute_code</param>
                <param name="type">file</param>
            </item>
            <!--<item name="component" xsi:type="string">Vendor_Module/js/form/element/button</item>-->
            <item name="label" xsi:type="string" translate="true">Custom Attribute Label</item>
        </item>
    </argument>
</field>

app/code/Vendor/Module/view/base/web/template/form/element/custom-button.html

<if args="initialValue">
    <img attr="src: initialValue, id: elementId+'_img'" class="small-image-preview v-middle" width="75" />
</if>
<input class="admin__control-text" type="hidden" data-bind="
        event: {change: userChanges},
        value: value,
        hasFocus: focused,
        valueUpdate: valueUpdate,
        attr: {
            name: inputName,
            placeholder: placeholder,
            'aria-describedby': noticeId,
            id: elementId,
            disabled: disabled
    }" />
<button type="button"
        css="
            'action-advanced': $data.displayAsLink,
            'action-secondary': !$data.displayAsLink
        "
        attr="'data-index': index, 'data-url': dialogUrl, id: elementId+'_button'"
        onClick="MediabrowserUtility.openDialog(this.getAttribute('data-url'))">
    <span attr="id: elementId+'_bttext'">Select Image</span>
</button>

The result is I see a button on category edit page:

enter image description here

when I click the button, there is a pop-up with Media Browser

enter image description here

The target input box's id was passed from category_form.xml to the custom-button.html, so the encoded url of the image selected in the media browser will get populated in the hidden input box that was put before the button in the html file.

Now when this category is saved, the encoded url have to be decoded and saved in the DB (I'll skip that code), so when we load the page again the preview of the image will be available.

Licensed under: CC-BY-SA with attribution
Not affiliated with magento.stackexchange
scroll top