Add UI-Select with search filter using the block method on the Admin form in Magento 2 – Beragampengetahuan
1 min read

Add UI-Select with search filter using the block method on the Admin form in Magento 2 – Beragampengetahuan

Here we learn how to add or create a UI-Select field using the block method on the Admin form.

Let’s start step by step.
You must have installed your custom Module on which you are going to implement this.

Step 1: We need to create the layout file to define the admin form in view/adminhtml/layout/webkulblog_account_edit.xml :

<?xml version="1.0"?>
<!--
/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright beragampengetahuan Software Private Limited (
 * @license   
 */
-->
<page xmlns:xsi=" layout="admin-2columns-left" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
    <update handle="styles"/>
    <update handle="editor"/>
    <body>
        <referenceBlock name="menu">
            <action method="setActive">
               <argument name="itemId" xsi:type="string">
                        Webkul_Custom:webkulblog
                    </argument>
        </action>
        </referenceBlock>
        <referenceBlock name="page.title">
            <action method="setTitleClass">
            <argument name="class" xsi:type="string">
                        complex
                    </argument>
        </action>
        </referenceBlock>
    </body>
</page>

Step 2: Create the block file, beragampengetahuan\Custom\Block\Adminhtml\Account\Edit.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */
namespace beragampengetahuan\Custom\Block\Adminhtml\Account;

class Edit extends \Magento\Backend\Block\Widget\Form\Container
{
    /**
     * Initialize
     *
     * @return void
     */
    protected function _construct()
    {
        $this->_objectId = 'entity_id';
        $this->_blockGroup = 'Webkul_Custom';
        $this->_controller = 'adminhtml_account';
        parent::_construct();
        if ($this->_isAllowedAction('Webkul_Custom::accountedit')) {
            $this->buttonList->update('save', 'label', __('Save Account'));
        } else {
            $this->buttonList->remove('save');
        }
        $this->buttonList->remove('delete');
        $this->buttonList->remove('reset');
    }

    /**
     * Retrieve text for header element depending on loaded Group
     *
     * @return \Magento\Framework\Phrase
     */
    public function getHeaderText()
    {
            return __('New Blog Account');
    }

    /**
     * Check permission for passed action
     *
     * @param string $resourceId
     * @return bool
     */
    protected function _isAllowedAction($resourceId)
    {
        return $this->_authorization->isAllowed($resourceId);
    }
}

Step 3: Create the block file, beragampengetahuan\Custom\Block\Adminhtml\Account\Edit\Tabs.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */

namespace beragampengetahuan\Custom\Block\Adminhtml\Account\Edit;

class Tabs extends \Magento\Backend\Block\Widget\Tabs
{
    /**
     * @param \Magento\Backend\Block\Template\Context $context
     * @param \Magento\Framework\Json\EncoderInterface $jsonEncoder
     * @param \Magento\Backend\Model\Auth\Session $authSession
     * @param array $data
     */
    public function __construct(
        \Magento\Backend\Block\Template\Context $context,
        \Magento\Framework\Json\EncoderInterface $jsonEncoder,
        \Magento\Backend\Model\Auth\Session $authSession,
        array $data = []
    ) {
        parent::__construct($context, $jsonEncoder, $authSession, $data);
    }

    /**
     * Construct
     *
     * @return void
     */
    protected function _construct()
    {
        parent::_construct();
        $this->setId('blog_account_tab');
        $this->setDestElementId('edit_form');
        $this->setTitle(__('Blog Account Information'));
    }

    /**
     * Prepare Layout
     *
     * @return $this
     */
    protected function _prepareLayout()
    {
        $block = \beragampengetahuan\Custom\Block\Adminhtml\Account\Edit\Tab\BlogAccount::class;
        $this->addTab(
            'blog_account_info',
            [
                'label' => __('Blog Account'),
                'content' => $this->getLayout()->createBlock($block, 'blog_account_info')->toHtml()
            ]
        );
        return parent::_prepareLayout();
    }
}

Step 4: Create the block file, beragampengetahuan\Custom\Block\Adminhtml\Account\Edit\Tab\BlogAccount.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */

namespace beragampengetahuan\Custom\Block\Adminhtml\Account\Edit\Tab;

use Magento\Backend\Block\Widget\Form\Generic;
use Magento\Backend\Block\Widget\Tab\TabInterface;
use beragampengetahuan\Custom\Block\Adminhtml\Widget\Form\Element\FilterSelect;

class BlogAccount extends Generic implements TabInterface
{

    /**
     * @param \Magento\Backend\Block\Template\Context $context
     * @param \Magento\Framework\Registry $registry
     * @param \Magento\Framework\Data\FormFactory $formFactory
     * @param array $data
     */
    public function __construct(
        \Magento\Backend\Block\Template\Context $context,
        \Magento\Framework\Registry $registry,
        \Magento\Framework\Data\FormFactory $formFactory,
        array $data = []
    ) {
        parent::__construct($context, $registry, $formFactory, $data);
    }

    /**
     * Prepare form
     *
     * @return $this
     */
    protected function _prepareForm()
    {
        $model = $this->_coreRegistry->registry('business_list_model');
        $form = $this->_formFactory->create();
        $fieldset = $form->addFieldset(
            'base_fieldset',
            ['legend' => __('Blog Account'), 'class' => 'fieldset-wide']
        );

        $fieldset->addType('filterselect', FilterSelect::class);
        if ($model->getId()) {
            $fieldset->addField('entity_id', 'hidden', ['name' => 'entity_id']);
        }

        $fieldset->addField(
            'user_name',
            'text',
            [
                'name' => 'user_name',
                'label' => __('User Name'),
                'title' => __('User Name'),
                'required' => true,
                'note' => __('Set the unique name for account.')
            ]
        );
        $fieldset->addField(
            'access_data',
            'filterselect', //custom type
            [
                'name' => 'access_data',
                'label' => __('Access data'),
                'options' => $this->getOptions(),
                'multiple' => true,
                'required' => true,
            ]
        );

        if (!empty($model->getData())) {
            $data = $model->getData();
            if (isset($data['access_data'])) {
                $data['access_data'] = explode(',', $data['access_data'] ?? '');
            }
            $form->setValues($data);
        }
        $this->setForm($form);
        return parent::_prepareForm();
    }

    /**
     * Get options
     *
     * @return array
     */
    public function getOptions()
    {
        return [
            ["value" => "1", "label" => "Customer"],
            ["value" => "2", "label" => "Admin"],
            ["value" => "3", "label" => "Seller"],
            ["value" => "4", "label" => "Guest"],
        ];
    }

    /**
     * Prepare label for tab
     *
     * @return \Magento\Framework\Phrase
     */
    public function getTabLabel()
    {
        return __('Blog Account');
    }

    /**
     * Prepare title for tab
     *
     * @return \Magento\Framework\Phrase
     */
    public function getTabTitle()
    {
        return __('Blog Account');
    }

    /**
     * CanShowTab
     *
     * @return bool
     */
    public function canShowTab()
    {
        return true;
    }

    /**
     * IsHidden
     *
     * @param bool
     */
    public function isHidden()
    {
        return false;
    }

    /**
     * Check permission for passed action
     *
     * @param string $resourceId
     * @return bool
     */
    protected function _isAllowedAction($resourceId)
    {
        return $this->_authorization->isAllowed($resourceId);
    }
}

Step-5: Add the custom type in block form using $fieldset->addType(‘filterselect’, FilterSelect::class);, This custom type’s “filterselect” field data handling and rendering by block file : beragampengetahuan\Custom\Block\Adminhtml\Widget\Form\Element\FilterSelect.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */

namespace beragampengetahuan\Custom\Block\Adminhtml\Widget\Form\Element;

use Magento\Framework\Data\Form\Element\AbstractElement;
use Magento\Framework\Data\Form\Element\Factory as ElementFactory;
use Magento\Framework\Data\Form\Element\CollectionFactory;
use Magento\Framework\Escaper;
use Magento\Framework\Serialize\SerializerInterface;

/**
 * Class FilterSelect.
 */
class FilterSelect extends AbstractElement
{
    /**
     * @var \Magento\Framework\View\LayoutInterface
     */
    protected $layout;

    /**
     * @var SerializerInterface
     */
    protected $serializer;

    /**
     * Constructor.
     *
     * @param ElementFactory    $elementFactory
     * @param CollectionFactory $collectionFactory
     * @param Escaper           $escaper
     * @param \Magento\Framework\View\LayoutInterface $layout
     * @param SerializerInterface $serializer
     * @param array             $data
     */
    public function __construct(
        ElementFactory $elementFactory,
        CollectionFactory $collectionFactory,
        Escaper $escaper,
        \Magento\Framework\View\LayoutInterface $layout,
        SerializerInterface $serializer,
        array $data = []
    ) {
        parent::__construct($elementFactory, $collectionFactory, $escaper, $data);
        $this->layout = $layout;
        $this->serializer = $serializer;
        $this->setType('filterselect');
    }

    /**
     * @inheritdoc
     */
    public function getElementHtml()
    {
        $html = $this->layout->createBlock(\Magento\Framework\View\Element\Template::class)
        ->setTemplate('Webkul_Custom::business/filterselect.phtml')
        ->setTemplateConfiguration($this->getCustomConfiguration())
        ->toHtml();
        $html .= $this->getAfterElementHtml();
        return $html;
    }

    /**
     * Get custom configuration
     *
     * @return string
     */
    public function getCustomConfiguration()
    {
        $data = $this->getData();
        $defultConfiguration = $this->getDefaultConfiguration();
        foreach($defultConfiguration as $key => $configuration){
            if(isset($data[$key])) {
                $defultConfiguration[$key] = $data[$key];
            }
        }
        return $this->serializer->serialize($defultConfiguration);
    }

    /**
     * Get defaults configuration
     *
     * @return array
     */
    public function getDefaultConfiguration()
    {
        $data = $this->getData();
        $configurationData =[
            "options" => [],
            "listVisible" => false,
            "value" => [],
            'filterOptions' => true,
            "chipsEnabled" => true,
            "itemsQuantity" => '',
            "filterInputValue" =>'',
            "filterOptionsFocus" => false,
            "multiselectFocus" => false,
            "multiple" => true,
            "selectType" =>'tree',
            "lastSelectable" => false,
            "showFilteredQuantity" => true,
            "showCheckbox" => false,
            "levelsVisibility" => true,
            "openLevelsAction" => true,
            "showOpenLevelsActionIcon" => true,
            "optgroupLabels" => false,
            "closeBtn" => true,
            "showPath" => true,
            "labelsDecoration" => false,
            "disableLabel" => false,
            "filterRateLimit" => 500,
            "closeBtnLabel" => __('Done'),
            "quantityPlaceholder" => __('options'),
            "hoverClass" => '_hover',
            "selectedPlaceholders" => [
                "defaultPlaceholder" => __('Select...'),
                "lotPlaceholders" => __('Selected')
            ],
            "component" => "Webkul_Custom/js/filterselect", //custom component file
            "template" => "Webkul_Custom/filterselect", //custom template file
            "elementData" => [
                "name" =>  $this->getName(),
                "id" => $this->getHtmlId(),
            ],
            "required_entry" => isset($data['required']) ? $data['required'] : false
       ];
        return  $configurationData;
    }
}

Step 6: Create a phtml template file which is mentioned in getElementHtml() method of Step 5, view/adminhtml/templates/business/filterselect.phtml

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */
?>
                <div data-bind="scope: 'customFilterSelect'">
                    <!-- ko template: getTemplate() --><!-- /ko -->
                </div>
                <script type="text/x-magento-init">
                    {
                            "*": {
                                "Magento_Ui/js/core/app": {
                                    "components": {
                                        "customFilterSelect": <?= /* @noEscape */ $block->getTemplateConfiguration() ?>
                                    }
                                }
                            }
                        }
                    </script>

Step 7: Create a custom component file which is mentioned in getDefaultConfiguration() method of Step 5, view/adminhtml/web/js/filterselect.js

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */
define([
    'underscore',
    'Magento_Ui/js/form/element/abstract',
    'Magento_Ui/js/lib/key-codes',
    'mage/translate',
    'ko',
    'jquery',
    'Magento_Ui/js/lib/view/utils/async'
], function (_, Abstract, keyCodes, $t, ko, $) {
    'use strict';

    var isTouchDevice = typeof document.ontouchstart !== 'undefined';

    /**
     * Processing options list
     *
     * @param {Array} array - Property array
     * @param {String} separator - Level separator
     * @param {Array} created - list to add new options
     *
     * @return {Array} Plain options list
     */
    function flattenCollection(array, separator, created)
    {
        var i = 0,
            length,
            childCollection;

        array = _.compact(array);
        length = array.length;
        created = created || [];

        for (i; i < length; i++) {
            created.push(array[i]);

            if (array[i].hasOwnProperty(separator)) {
                childCollection = array[i][separator];
                delete array[i][separator];
                flattenCollection.call(this, childCollection, separator, created);
            }
        }

        return created;
    }

    /**
     * Set levels to options list
     *
     * @param {Array} array - Property array
     * @param {String} separator - Level separator
     * @param {Number} level - Starting level
     * @param {String} path - path to root
     *
     * @returns {Array} Array with levels
     */
    function setProperty(array, separator, level, path)
    {
        var i = 0,
            length,
            nextLevel,
            nextPath;

        array = _.compact(array);
        length = array.length;
        level = level || 0;
        path = path || '';

        for (i; i < length; i++) {
            if (array[i]) {
                _.extend(array[i], {
                    level: level,
                    path: path
                });
            }

            if (array[i].hasOwnProperty(separator)) {
                nextLevel = level + 1;
                nextPath = path ? path + '.' + array[i].label : array[i].label;
                setProperty.call(this, array[i][separator], separator, nextLevel, nextPath);
            }
        }

        return array;
    }

    /**
     * Preprocessing options list
     *
     * @param {Array} nodes - Options list
     *
     * @return {Object} Object with property - options(options list)
     *      and cache options with plain and tree list
     */
    function parseOptions(nodes)
    {
        var caption,
            value,
            cacheNodes,
            copyNodes;

        nodes = setProperty(nodes, 'optgroup');
        copyNodes = JSON.parse(JSON.stringify(nodes));
        cacheNodes = flattenCollection(copyNodes, 'optgroup');

        nodes = _.map(nodes, function (node) {
            value = node.value;

            if (value == null || value === '') {
                if (_.isUndefined(caption)) {
                    caption = node.label;
                }
            } else {
                return node;
            }
        });

        return {
            options: _.compact(nodes),
            cacheOptions: {
                plain: _.compact(cacheNodes),
                tree: _.compact(nodes)
            }
        };
    }

    return Abstract.extend({
        defaults: {
            options: [],
            listVisible: false,
            value: [],
            filterOptions: false,
            chipsEnabled: true,
            required_entry:false,
            itemsQuantity: '',
            filterInputValue: '',
            filterOptionsFocus: false,
            multiselectFocus: false,
            multiple: true,
            selectType: 'tree',
            lastSelectable: false,
            showFilteredQuantity: true,
            showCheckbox: true,
            levelsVisibility: true,
            openLevelsAction: true,
            showOpenLevelsActionIcon: true,
            optgroupLabels: false,
            closeBtn: true,
            showPath: true,
            labelsDecoration: false,
            disableLabel: false,
            filterRateLimit: 500,
            closeBtnLabel: $t('Done'),
            optgroupTmpl: 'ui/grid/filters/elements/ui-select-optgroup',
            quantityPlaceholder: $t('options'),
            hoverClass: '_hover',
            rootListSelector: 'ul.admin__action-multiselect-menu-inner._root',
            visibleOptionSelector: 'li.admin__action-multiselect-menu-inner-item:visible',
            actionTargetSelector: '.action-menu-item',
            selectedPlaceholders: {
                defaultPlaceholder: $t('Select...'),
                lotPlaceholders: $t('Selected')
            },
            separator: 'optgroup',
            listens: {
                listVisible: 'cleanHoveredElement',
                filterInputValue: 'filterOptionsList',
                options: 'checkOptionsList'
            },
            presets: {
                single: {
                    showCheckbox: false,
                    chipsEnabled: false,
                    closeBtn: false
                },
                optgroup: {
                    showCheckbox: false,
                    lastSelectable: true,
                    optgroupLabels: true,
                    openLevelsAction: false,
                    labelsDecoration: true,
                    showOpenLevelsActionIcon: false
                }
            }
        },

        /**
         * Initializes UISelect component.
         *
         * @returns {UISelect} Chainable.
         */
        initialize: function () {
            this._super();
            $.async(
                this.rootListSelector,
                this,
                this.onRootListRender.bind(this)
            );

            return this;
        },

        /**
         * Parses options and merges the result with instance
         * Set defaults according to mode and levels configuration
         *
         * @param  {Object} config
         * @returns {Object} Chainable.
         */
        initConfig: function (config) {
            var result = parseOptions(config.options),
                defaults = this.constructor.defaults,
                multiple = _.isBoolean(config.multiple) ? config.multiple : defaults.multiple,
                type = config.selectType || defaults.selectType,
                showOpenLevelsActionIcon = _.isBoolean(config.showOpenLevelsActionIcon) ?
                    config.showOpenLevelsActionIcon :
                    defaults.showOpenLevelsActionIcon,
                openLevelsAction = _.isBoolean(config.openLevelsAction) ?
                    config.openLevelsAction :
                    defaults.openLevelsAction;

            multiple = !multiple ? 'single' : false;
            config.showOpenLevelsActionIcon = showOpenLevelsActionIcon && openLevelsAction;
            _.extend(config, result, defaults.presets[multiple], defaults.presets[type]);
            this._super();

            return this;
        },

        /**
         * Check child optgroup
         */
        hasChildList: function () {
            return _.find(this.options(), function (option) {
                return !!option[this.separator];
            }, this);
        },

        /**
         * Check tree mode
         */
        isTree: function () {
            return this.hasChildList() && this.selectType !== 'optgroup';
        },

        /**
         * Add option to lastOptions array
         *
         * @param {Object} data
         * @returns {Boolean}
         */
        addLastElement: function (data) {
            if (!data.hasOwnProperty(this.separator)) {
                !this.cacheOptions.lastOptions ? this.cacheOptions.lastOptions = [] : false;

                if (!_.findWhere(this.cacheOptions.lastOptions, { value: data.value })) {
                    this.cacheOptions.lastOptions.push(data);
                }

                return true;
            }

            return false;
        },

        /**
         * Check options length and set to cache
         * if some options is added
         *
         * @param {Array} options - ui select options
         */
        checkOptionsList: function (options) {
            if (options.length > this.cacheOptions.plain.length) {
                this.cacheOptions.plain = options;
                this.setCaption();
            }
        },

        /**
         * Check label decoration
         */
        isLabelDecoration: function (data) {
            return data.hasOwnProperty(this.separator) && this.labelsDecoration;
        },

        /**
         * Calls 'initObservable' of parent, initializes 'options' and 'initialOptions'
         *     properties, calls 'setOptions' passing options to it
         *
         * @returns {Object} Chainable.
         */
        initObservable: function () {
            this._super();
            this.observe([
                'listVisible',
                'placeholder',
                'multiselectFocus',
                'options',
                'itemsQuantity',
                'filterInputValue',
                'filterOptionsFocus'
            ]);

            this.filterInputValue.extend({
                rateLimit: this.filterRateLimit
            });

            return this;
        },

        /**
         * object with key - keyname and value - handler function for this key
         *
         * @returns {Object} Object with handlers function name.
         */
        keyDownHandlers: function () {
            return {
                enterKey: this.enterKeyHandler,
                escapeKey: this.escapeKeyHandler,
                spaceKey: this.enterKeyHandler,
                pageUpKey: this.pageUpKeyHandler,
                pageDownKey: this.pageDownKeyHandler
            };
        },

        /**
         * Processing level visibility for levels
         *
         * @param {Object} data - element data
         *
         * @returns {Boolean} level visibility.
         */
        showLevels: function (data) {
            var curLevel = ++data.level,
                isVisible;

            if (data.visible) {
                isVisible = data.visible();
            } else {
                isVisible = !!data.hasOwnProperty(this.separator) &&
                    _.isBoolean(this.levelsVisibility) &&
                    this.levelsVisibility ||
                    data.hasOwnProperty(this.separator) && parseInt(this.levelsVisibility, 10) >= curLevel;

                data.visible = ko.observable(isVisible);
                data.isVisited = isVisible;
            }

            return isVisible;
        },

        /**
         * Processing level visibility for levels
         *
         * @param {Object} data - element data
         *
         * @returns {Boolean} level visibility.
         */
        getLevelVisibility: function (data) {
            if (data.visible) {
                return data.visible();
            }

            return this.showLevels(data);
        },

        /**
         * Set option to options array.
         *
         * @param {Object} option
         * @param {Array} options
         */
        setOption: function (option, options) {
            var copyOptionsTree;

            options = options || this.cacheOptions.tree;

            _.each(options, function (opt) {
                if (opt.value == option.parent) { //eslint-disable-line eqeqeq
                    delete  option.parent;
                    opt[this.separator] ? opt[this.separator].push(option) : opt[this.separator] = [option];
                    copyOptionsTree = JSON.parse(JSON.stringify(this.cacheOptions.tree));
                    this.cacheOptions.plain = flattenCollection(copyOptionsTree, this.separator);
                    this.options(this.cacheOptions.tree);
                } else if (opt[this.separator]) {
                    this.setOption(option, opt[this.separator]);
                }
            }, this);
        },

        /**
         * Handler outerClick event. Closed options list
         */
        outerClick: function () {
            this.listVisible() ? this.listVisible(false) : false;

            if (isTouchDevice) {
                this.multiselectFocus(false);
            }
        },

        /**
         * Handler keydown event to filter options input
         *
         * @returns {Boolean} Returned true for emersion events
         */
        filterOptionsKeydown: function (data, event) {
            var key = keyCodes[event.keyCode];

            !this.isTabKey(event) ? event.stopPropagation() : false;

            if (key === 'pageDownKey' || key === 'pageUpKey') {
                event.preventDefault();
                this.filterOptionsFocus(false);
                this.cacheUiSelect.focus();
            }

            this.keydownSwitcher(data, event);

            return true;
        },

        /**
         * Filtered options list by value from filter options list
         */
        filterOptionsList: function () {
            var value = this.filterInputValue().trim().toLowerCase(),
                array = [];

            if (value && value.length < 2) {
                return false;
            }

            this.cleanHoveredElement();

            if (!value) {
                this.renderPath = false;
                this.options(this.cacheOptions.tree);
                this._setItemsQuantity(false);

                return false;
            }

            this.showPath ? this.renderPath = true : false;

            if (this.filterInputValue()) {
                array = this.selectType === 'optgroup' ?
                    this._getFilteredArray(this.cacheOptions.lastOptions, value) :
                    this._getFilteredArray(this.cacheOptions.plain, value);

                if (!value.length) {
                    this.options(this.cacheOptions.plain);
                    this._setItemsQuantity(this.cacheOptions.plain.length);
                } else {
                    this.options(array);
                    this._setItemsQuantity(array.length);
                }

                return false;
            }

            this.options(this.cacheOptions.plain);
        },

        /**
         * Filtered options list by value from filter options list
         *
         * @param {Array} list - option list
         * @param {String} value
         *
         * @returns {Array} filters result
         */
        _getFilteredArray: function (list, value) {
            var i = 0,
                array = [],
                curOption;

            for (i; i < list.length; i++) {
                curOption = list[i].label.toLowerCase();

                if (curOption.indexOf(value) > -1) {
                    array.push(list[i]); /*eslint max-depth: [2, 4]*/
                }
            }

            return array;
        },

        /**
         * Get path to current option
         *
         * @param {Object} data - option data
         * @returns {String} path
         */
        getPath: function (data) {
            var pathParts,
                createdPath = '';

            if (this.renderPath) {
                pathParts = data.path.split('.');
                _.each(pathParts, function (curData) {
                    createdPath = createdPath ? createdPath + ' / ' + curData : curData;
                });

                return createdPath;
            }
        },

        /**
         * Set filtered items quantity
         *
         * @param {Object} data - option data
         */
        _setItemsQuantity: function (data) {
            if (this.showFilteredQuantity) {
                data || parseInt(data, 10) === 0 ?
                    this.itemsQuantity(data + ' ' + this.quantityPlaceholder) :
                    this.itemsQuantity('');
            }
        },

        /**
         * Remove element from selected array
         */
        removeSelected: function (value, data, event) {
            event ? event.stopPropagation() : false;
            this.value.remove(value);
        },

        /**
         * Checked key name
         *
         * @returns {Boolean}
         */
        isTabKey: function (event) {
            return keyCodes[event.keyCode] === 'tabKey';
        },

        /**
         * Clean hoveredElement variable
         *
         * @returns {Object} Chainable
         */
        cleanHoveredElement: function () {
            if (this.hoveredElement) {
                $(this.hoveredElement)
                    .children(this.actionTargetSelector)
                    .removeClass(this.hoverClass);

                this.hoveredElement = null;
            }

            return this;
        },

        /**
         * Check selected option
         *
         * @param {String} value - option value
         * @return {Boolean}
         */
        isSelected: function (value) {
            return this.multiple ? _.contains(this.value(), value) : this.value() === value;
        },

        /**
         * Check optgroup label
         *
         * @param {Object} data - element data
         * @return {Boolean}
         */
        isOptgroupLabels: function (data) {
            return data.hasOwnProperty(this.separator) && this.optgroupLabels;
        },

        /**
         * Check hovered option
         *
         * @param {Object} data - element data
         * @return {Boolean}
         */
        isHovered: function (data) {
            var element = this.hoveredElement,
                elementData;

            if (!element) {
                return false;
            }

            elementData = ko.dataFor(this.hoveredElement);

            return data.value === elementData.value;
        },

        /**
         * Toggle list visibility
         *
         * @returns {Object} Chainable
         */
        toggleListVisible: function () {
            this.listVisible(!this.listVisible());

            return this;
        },

        /**
         * Get selected element labels
         *
         * @returns {Array} array labels
         */
        getSelected: function () {
            var selected = this.value();

            return this.cacheOptions.plain.filter(function (opt) {
                return _.isArray(selected) ?
                    _.contains(selected, opt.value) :
                selected == opt.value;//eslint-disable-line eqeqeq
            });
        },

        /**
         * Toggle activity list element
         *
         * @param {Object} data - selected option data
         * @returns {Object} Chainable
         */
        toggleOptionSelected: function (data) {
            var isSelected = this.isSelected(data.value);

            if (this.lastSelectable && data.hasOwnProperty(this.separator)) {
                return this;
            }

            if (!this.multiple) {
                if (!isSelected) {
                    this.value(data.value);
                }
                this.listVisible(false);
            } else {
                if (!isSelected) { /*eslint no-lonely-if: 0*/
                    this.value.push(data.value);
                } else {
                    this.value(_.without(this.value(), data.value));
                }
            }

            return this;
        },

        /**
         * Change visibility to child level
         *
         * @param {Object} data - element data
         */
        openChildLevel: function (data) {
            var contextElement = data,
                isVisible;

            if (this.openLevelsAction && data.hasOwnProperty(this.separator) && _.isBoolean(this.levelsVisibility) || this.openLevelsAction && data.hasOwnProperty(this.separator) && parseInt(this.levelsVisibility, 10) <= data.level) {
                isVisible = !contextElement.visible();

                if (isVisible && !contextElement.isVisited) {
                    contextElement.isVisited = true;
                }

                contextElement.visible(isVisible);
            }
        },

        /**
         * Check selected elements
         *
         * @returns {Boolean}
         */
        hasData: function () {
            if (!this.value()) {
                this.value([]);
            }

            return this.value() ? !!this.value().length : false;
        },

        /**
         * @deprecated
         */
        onMousemove: function () {},

        /**
         * Handles hover on list items.
         *
         * @param {Object} event - mousemove event
         */
        onDelegatedMouseMouve: function (event) {
            var target = $(event.currentTarget).closest(this.visibleOptionSelector)[0];

            if (this.isCursorPositionChange(event) || this.hoveredElement === target) {
                return;
            }

            this._hoverTo(target);
            this.setCursorPosition(event);
        },

        /**
         * Get option index
         *
         * @param {Object} data - object with data about this element
         *
         * @returns {Number}
         */
        getOptionIndex: function (data) {
            var index;

            _.each(this.cacheOptions.plain, function (opt, id) {
                if (data.value === opt.value) {
                    index = id;
                }
            });

            return index;
        },

        /**
         * Set X and Y cursor position
         *
         * @param {Object} event - mousemove event
         */
        setCursorPosition: function (event) {
            this.cursorPosition = {
                x: event.pageX,
                y: event.pageY
            };
        },

        /**
         * Check previous and current cursor position
         *
         * @param {Object} event - mousemove event
         * @returns {Boolean}
         */
        isCursorPositionChange: function (event) {
            return this.cursorPosition &&
                this.cursorPosition.x === event.pageX &&
                this.cursorPosition.y === event.pageY;
        },

        /**
         * Set true to observable variable multiselectFocus
         * @param {Object} ctx
         * @param {Object} event - focus event
         */
        onFocusIn: function (ctx, event) {
            !this.cacheUiSelect ? this.cacheUiSelect = event.target : false;
            this.multiselectFocus(true);
        },

        /**
         * Set false to observable variable multiselectFocus
         * and close list
         */
        onFocusOut: function () {
            this.multiselectFocus(false);
        },

        /**
         * Handler enter key, if select list is closed - open select,
         * if select list is open toggle selected current option
         */
        enterKeyHandler: function () {

            if (this.filterOptionsFocus()) {
                return false;
            }

            if (this.listVisible()) {
                if (this.hoveredElement) {
                    this.toggleOptionSelected(ko.dataFor(this.hoveredElement));
                }
            } else {
                this.setListVisible(true);
            }
        },

        /**
         * Handler escape key, if select list is open - closes it,
         */
        escapeKeyHandler: function () {
            this.listVisible() ? this.setListVisible(false) : false;
        },

        /**
         * Handler pageDown key, selected next option in list, if current option is last
         * selected first option in list
         */
        pageDownKeyHandler: function () {
            this._setHoverToElement(1);
        },

        /**
         * Get jQuery element by option data
         *
         * @param {Object} data - option data
         *
         * @returns {Object} jQuery element
         */
        _getElemByData: function (data) {
            var i = 0,
                list = $(this.cacheUiSelect).find('li'),
                length = this.options().length,
                result;

            for (i; i < length; i++) {
                if (this.options()[i].value === data.value) {
                    result = $(list[i]);
                }
            }

            return result;
        },

        /**
         * Set hover to visible element
         *
         * @param {Number} direction - iterator
         */
        _setHoverToElement: function (direction) {
            var element;

            if (direction ===  1) {
                element = this._getNextElement();
            } else if (direction === -1) {
                element = this._getPreviousElement();
            }

            if (element) {
                this._hoverTo(element);
                this._scrollTo(element);
            }
        },

        /**
         * Find current hovered element
         * and change scroll position
         *
         * @param {Number} element - element index
         */
        _scrollTo: function (element) {
            var curEl = $(element).children(this.actionTargetSelector),
                wrapper = $(this.rootList),
                curElPos = {},
                wrapperPos = {};

            curElPos.start = curEl.offset().top;
            curElPos.end = curElPos.start + curEl.outerHeight();

            wrapperPos.start = wrapper.offset().top;
            wrapperPos.end = wrapperPos.start + wrapper.height();

            if (curElPos.start < wrapperPos.start) {
                wrapper.scrollTop(wrapper.scrollTop() - (wrapperPos.start - curElPos.start));
            } else if (curElPos.end > wrapperPos.end) {
                wrapper.scrollTop(wrapper.scrollTop() + curElPos.end - wrapperPos.end);
            }
        },

        /**
         * Handler pageUp key, selected previous option in list, if current option is first -
         * selected last option in list
         */
        pageUpKeyHandler: function () {
            this._setHoverToElement(-1);
        },

        /**
         * Switcher to parse keydown event and delegate event to needful method
         *
         * @param {Object} data - element data
         * @param {Object} event - keydown event
         * @returns {Boolean} if handler for this event doesn't found return true
         */
        keydownSwitcher: function (data, event) {
            var keyName = keyCodes[event.keyCode];

            if (this.isTabKey(event)) {
                if (!this.filterOptionsFocus() && this.listVisible() && this.filterOptions) {
                    this.cacheUiSelect.blur();
                    this.filterOptionsFocus(true);
                    this.cleanHoveredElement();

                    return false;
                }
                this.listVisible(false);

                return true;
            }

            if (this.keyDownHandlers().hasOwnProperty(keyName)) {
                this.keyDownHandlers()[keyName].apply(this, arguments);
            } else {
                return true;
            }
        },

        /**
         * Set caption
         */
        setCaption: function () {
            var length;

            if (!_.isArray(this.value()) && this.value()) {
                length = 1;
            } else if (this.value()) {
                length = this.value().length;
            } else {
                this.value([]);
                length = 0;
            }

            if (length > 1) {
                this.placeholder(length + ' ' + this.selectedPlaceholders.lotPlaceholders);
            } else if (length && this.getSelected().length) {
                this.placeholder(this.getSelected()[0].label);
            } else {
                this.placeholder(this.selectedPlaceholders.defaultPlaceholder);
            }

            return this.placeholder();
        },

        /**
         * Set list status, open or close
         *
         * @param {Boolean} value - variable for set list visible status
         */
        setListVisible: function (value) {
            this.listVisible(value);
        },

        /**
         * Processes preview for option by it's value, and sets the result
         * to 'preview' observable
         *
         * @returns {String}
         */
        getPreview: function () {
            var selected = this.getSelected();

            return selected.map(function (option) {
                return option.label;
            }).join(', ');
        },

        /**
         * Defines previous option element to
         * the one that is currently hovered.
         *
         * @returns {Element}
         */
        _getPreviousElement: function () {
            var currentElement = this.hoveredElement,
                lastElement    = this._getLastIn(this.rootList),
                previousElement;

            if (!currentElement) {
                return lastElement;
            }

            previousElement = $(currentElement).prev()[0];

            return this._getLastIn(previousElement) ||
                previousElement ||
                this._getFirstParentOf(currentElement) ||
                lastElement;
        },

        /**
         * Defines next option element to
         * the one that is currently hovered.
         *
         * @returns {Element}
         */
        _getNextElement: function () {
            var currentElement = this.hoveredElement,
                firstElement   = this._getFirstIn(this.rootList);

            if (!currentElement) {
                return firstElement;
            }

            return this._getFirstIn(currentElement) ||
                $(currentElement).next()[0] ||
                this._getParentsOf(currentElement).next()[0] ||
                firstElement;
        },

        /**
         * Returns first option element in provided scope.
         *
         * @param {Element} scope
         * @returns {Element}
         */
        _getFirstIn: function (scope) {
            return $(scope).find(this.visibleOptionSelector)[0];
        },

        /**
         * Returns last descendant option element in provided scope.
         *
         * @param {Element} scope
         * @returns {Element}
         */
        _getLastIn: function (scope) {
            return $(scope).find(this.visibleOptionSelector).last()[0];
        },

        /**
         * Returns a collection of parent option elements.
         *
         * @param {Element} scope
         * @returns {jQueryCollection}
         */
        _getParentsOf: function (scope) {
            return $(scope).parents(this.visibleOptionSelector);
        },

        /**
         * Returns first parent option element.
         *
         * @param {Element} scope
         * @returns {Element}
         */
        _getFirstParentOf: function (scope) {
            return this._getParentsOf(scope)[0];
        },

        /**
         * Sets hover class to provided option element.
         *
         * @param {Element} element
         */
        _hoverTo: function (element) {
            if (this.hoveredElement) {
                $(this.hoveredElement)
                    .children(this.actionTargetSelector)
                    .removeClass(this.hoverClass);
            }

            $(element)
                .children(this.actionTargetSelector)
                .addClass(this.hoverClass);

            this.hoveredElement = element;
        },

        /**
         * Callback which fires when root list element is rendered.
         *
         * @param {Element} element
         */
        onRootListRender: function (element) {
            var targetSelector = 'li > ' + this.actionTargetSelector;

            this.rootList = element;

            $(this.rootList).on(
                'mousemove',
                targetSelector,
                this.onDelegatedMouseMouve.bind(this)
            );
        }
    });
});

Step 8: Create a custom template file which is mentioned in getDefaultConfiguration() method of Step 5, view/adminhtml/web/template/filterselect.html

<!--
/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */
 -->
 
 <div
 class="admin__action-multiselect-wrap action-select-wrap"
 tabindex="0"
 data-bind="
 attr: {
     id: uid
 },
 css: {
     _active: listVisible,
     'admin__action-multiselect-tree': isTree()
 },
 event: {
     focusin: onFocusIn,
     focusout: onFocusOut,
     keydown: keydownSwitcher
 },
 outerClick: outerClick.bind($data)
 ">
   <!-- ko if: (!hasData() && multiple) -->
   <input type="hidden"
   data-bind="
   attr: {
       id: elementData.id,
       name: elementData.name+'[]',
       value: null
   }
 ">
  <!-- /ko -->
 <!-- ko ifnot: chipsEnabled -->
 <div
     class="action-select admin__action-multiselect"
     data-role="advanced-select"
     data-bind="
     css: {_active: multiselectFocus},
     click: function(data, event) {
         toggleListVisible(data, event)
     }
 ">
 <div class="admin__action-multiselect-text"
      data-role="selected-option"
      data-bind="text: setCaption()">
 </div>
<!-- ko foreach: { data: getSelected(), as: 'option'}  -->
<input type="hidden"
    data-bind="
    attr: {
        id: $parent.elementData.id + value,
        name: $parent.elementData.name +'[]',
        value: value
    }
">
<!-- /ko -->
 </div>
 <!-- /ko -->
 <!-- ko if: chipsEnabled -->
 <div
     class="action-select admin__action-multiselect"
     data-role="advanced-select"
     data-bind="
     css: {_active: multiselectFocus},
     click: function(data, event) {
         toggleListVisible(data, event)
     }
 ">
 <div class="admin__action-multiselect-text"
      data-bind="
         visible: !hasData(),
         i18n: selectedPlaceholders.defaultPlaceholder
 ">
 </div>
 <!-- ko foreach: { data: getSelected(), as: 'option'}  -->
     <span class="admin__action-multiselect-crumb">
         <span data-bind="text: label">
         </span>
         <button
                 class="action-close"
                 type="button"
                 data-action="remove-selected-item"
                 tabindex="-1"
                 data-bind="click: $parent.removeSelected.bind($parent, value)
         ">
             <span class="action-close-text" translate="'Close'"></span>
         </button>
     </span>
     <input type="hidden"
         data-bind="
         attr: {
             id: $parent.elementData.id + value,
             name: $parent.elementData.name +'[]',
             value: value
         }
     ">
 <!-- /ko -->
 </div>
 <!-- /ko -->
 <div class="action-menu"
  data-bind="css: { _active: listVisible }
 ">
 <!-- ko if: filterOptions -->
 <div class="admin__action-multiselect-search-wrap">
     <input
             class="admin__control-text admin__action-multiselect-search"
             data-role="advanced-select-text"
             type="text"
             data-bind="
         event: {
             keydown: filterOptionsKeydown
         },
         attr: {id: uid+2},
         valueUpdate: 'afterkeydown',
         value: filterInputValue,
         hasFocus: filterOptionsFocus
         ">
     <label
             class="admin__action-multiselect-search-label"
             data-action="advanced-select-search"
             data-bind="attr: {for: uid+2}
     ">
     </label>
     <div if="itemsQuantity"
          data-bind="text: itemsQuantity"
          class="admin__action-multiselect-search-count">
     </div>
 </div>
 <!-- /ko -->
 <ul class="admin__action-multiselect-menu-inner _root"
     data-bind="
         event: {
             mousemove: function(data, event){onMousemove($data, event)}
         }
     ">
     <!-- ko foreach: { data: options, as: 'option'}  -->
     <li class="admin__action-multiselect-menu-inner-item _root"
         data-bind="css: { _parent: $data.optgroup }"
         data-role="option-group">
         <div class="action-menu-item"
              data-bind="
                 css: {
                     _selected: $parent.isSelected(option.value),
                     _hover: $parent.isHovered(option, $element),
                     _expended: $parent.getLevelVisibility($data),
                     _unclickable: $parent.isLabelDecoration($data),
                     _last: $parent.addLastElement($data),
                     '_with-checkbox': $parent.showCheckbox
                 },
                 click: function(data, event){
                     $parent.toggleOptionSelected($data, event);
                 },
                 clickBubble: false
         ">
             <!-- ko if: $data.optgroup && $parent.showOpenLevelsActionIcon-->
             <div class="admin__action-multiselect-dropdown"
                  data-bind="
                     click: function(event){
                         $parent.openChildLevel($data, $element, event);
                     },
                     clickBubble: false
                  ">
             </div>
             <!-- /ko-->
             <!--ko if: $parent.showCheckbox-->
             <input
                     class="admin__control-checkbox"
                     type="checkbox"
                     tabindex="-1"
                     data-bind="attr: { 'checked': $parent.isSelected(option.value) }">
             <!-- /ko-->
             <label class="admin__action-multiselect-label">
                 <span data-bind="text: option.label"></span>
                 <span
                         if="$parent.getPath(option)"
                         class="admin__action-multiselect-item-path"
                         data-bind="text: $parent.getPath(option)"></span>
             </label>
         </div>
         <!-- ko if: $data.optgroup -->
         <!-- ko template: {name: $parent.optgroupTmpl, data: {root: $parent, current: $data}} -->
         <!-- /ko -->
         <!-- /ko-->
     </li>
     <!-- /ko -->
 </ul>
 <!-- ko if: $data.closeBtn -->
 <div class="admin__action-multiselect-actions-wrap">
     <button class="action-default"
             data-action="close-advanced-select"
             type="button"
             data-bind="click: outerClick">
         <span translate="closeBtnLabel"></span>
     </button>
 </div>
 <!-- /ko -->
 </div>
 </div>
  <!-- ko if: ($data.getSelected().length == 0 && required_entry) -->
  <input type="hidden"
  data-bind="
  attr: {
    name: 'custom_required',
    class: 'required-entry',
    value: null
  }
">
 <!-- /ko -->

Step 9: Create a block file for form, beragampengetahuan\Custom\Block\Adminhtml\Account\Edit\Form.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */

namespace beragampengetahuan\Custom\Block\Adminhtml\Account\Edit;

class Form extends \Magento\Backend\Block\Widget\Form\Generic
{
    /**
     * Init form
     *
     * @return void
     */
    protected function _construct()
    {
        parent::_construct();
        $this->setId('blog_account_form');
        $this->setTitle(__('Blog Account Information'));
    }

    /**
     * Prepare form
     *
     * @return $this
     */
    protected function _prepareForm()
    {
        $model = $this->_coreRegistry->registry('business_list_model');
        $form = $this->_formFactory->create(
            [
                'data' => [
                    'id' => 'edit_form',
                    'enctype' => 'multipart/form-data',
                    'action' => $this->getData('action'),
                    'method' => 'post'
                ]
            ]
        );
        if (!empty($model->getData())) {
            $data = $model->getData();
            if (isset($data['access_data'])) {
                $data['access_data'] = explode(',', $data['access_data'] ?? '');
            }
            $form->setValues($data);
        }
        $form->setUseContainer(true);
        $this->setForm($form);
        return parent::_prepareForm();
    }
}

Step 10: Create a controller file for layout webkulblog_account_edit.xml , beragampengetahuan\Custom\Controller\Adminhtml\Account\Edit.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */

namespace beragampengetahuan\Custom\Controller\Adminhtml\Account;

use Magento\Framework\Controller\ResultFactory;
use beragampengetahuan\Custom\Block\Adminhtml\Account\Edit as AccountEdit;
use beragampengetahuan\Custom\Block\Adminhtml\Account\Edit\Tabs;

class Edit extends \Magento\Backend\App\Action
{
    /**
     * @var string
     */
    public const ADMIN_RESOURCE = "Webkul_Custom::accountedit";

    /**
     * @var \Magento\Framework\Registry
     */
    private $registry;

    /**
     * @var \beragampengetahuan\Custom\Model\BusinessListFactory
     */
    protected $businessListFactory;

    /**
     * @param \Magento\Backend\App\Action\Context $context
     * @param \Magento\Framework\Registry $registry
     */
    public function __construct(
        \Magento\Backend\App\Action\Context $context,
        \Magento\Framework\Registry $registry,
        \beragampengetahuan\Custom\Model\BusinessListFactory $businessListFactory
    ) {
        $this->registry = $registry;
        $this->businessListFactory = $businessListFactory;
        parent::__construct($context);
    }

    /**
     * Execute
     *
     * @return \Magento\Backend\Model\View\Result\Page
     */
    public function execute()
    {
        try {
            $params = $this->getRequest()->getParams();
            $businessListModel = $this->businessListFactory->create();
            if (isset($params['entity_id']) && $params['entity_id']) {
                $businessListModel->load($params['entity_id']);
                if (!$businessListModel->getId()) {
                    $this->messageManager->addError(__('Requested account currently not available.'));
                    $resultRedirect = $this->resultRedirectFactory->create();
                    return $resultRedirect->setPath('*/*/');
                }
            }
            $this->registry->register('business_list_model', $businessListModel);
            $resultPage = $this->resultFactory->create(ResultFactory::TYPE_PAGE);
            $resultPage->setActiveMenu('Webkul_Custom::webkulblog');
            $resultPage->getConfig()->getTitle()->prepend(__('Account'));
            $resultPage->addContent($resultPage->getLayout()->createBlock(AccountEdit::class));
            $resultPage->addLeft($resultPage->getLayout()->createBlock(Tabs::class));
            return $resultPage;
        } catch (\Exception $e) {
            $this->messageManager->addError($e->getMessage());
            $this->_redirect('*/*/');
        }
    }
    /**
     * Check for is allowed
     *
     * @return boolean
     */
    protected function _isAllowed()
    {
        return $this->_authorization->isAllowed(self::ADMIN_RESOURCE);
    }
}

Step 11: Create a controller file for the save selected option, beragampengetahuan\Custom\Controller\Adminhtml\Account\Save.php

<?php

/**
 * beragampengetahuan Software.
 *
 * @category  beragampengetahuan
 * @package   Webkul_Custom
 * @author    beragampengetahuan
 * @copyright Copyright (c)  beragampengetahuan Software Private Limited (
 * @license   
 */

namespace beragampengetahuan\Custom\Controller\Adminhtml\Account;

use Magento\Backend\App\Action;
use Magento\Backend\App\Action\Context;
use Magento\Framework\View\Result\PageFactory;

class Save extends Action
{
    /**
     * @var Magento\Framework\View\Result\PageFactory
     */
    protected $resultPageFactory;

    /**
     * @var beragampengetahuan\Custom\Model\BusinessListFactory */
    protected $businessListFactory;

    /**
     * @var \Magento\Framework\Registry
     */
    protected $coreRegistry = null;

    /**
     * @param Context $context
     * @param PageFactory $resultPageFactory
     * @param \beragampengetahuan\Custom\Model\BusinessListFactory $businessListFactory
     * @param \Magento\Framework\Registry $coreRegistry
     */
    public function __construct(
        Context $context,
        PageFactory $resultPageFactory,
        \beragampengetahuan\Custom\Model\BusinessListFactory $businessListFactory,
        \Magento\Framework\Registry $coreRegistry
    ) {
        parent::__construct($context);
        $this->resultPageFactory = $resultPageFactory;
        $this->businessListFactory = $businessListFactory;
        $this->coreRegistry = $coreRegistry;
    }

    /**
     * Save User Data
     *
     * @return \Magento\Framework\App\Response\Http
     */
    public function execute()
    {
        $resultRedirect = $this->resultRedirectFactory->create();
        $data = $this->getRequest()->getParams();
        if (isset($data['user_name'])) {
            $userAcccessIds = '';
            if (isset($data['access_data'])) {
                $userAcccessIds = implode(',', $data['access_data']);
            }
            $data['access_data'] = $userAcccessIds;
            $businessList = $this->businessListFactory->create();
            $businessList->setData($data)->save();
            $id = $businessList->getId();
            $this->coreRegistry->register("entity_id", $id);
            $this->messageManager->addSuccess("User data has been saved.");
            return $resultRedirect->setPath('*/*/edit', ['entity_id' => $id]);
        } else {
            $this->messageManager->addError(
                __('Something went wrong while saving the user data.')
            );
            return $resultRedirect->setPath('*/*/edit');
        }
    }
}

After this, a ui-select with a search filter using the block method will be displayed on your form.

Screenshot-2024-01-23T201658.071

Change custom type UI select element configuration in Step 4:

Note: Custom field element configuration changed according to the mentioned configuration in getDefaultConfiguration() method of Step 5 file.

 $fieldset->addField(
            'access_data', //Element Id
            'filterselect', //custom type
            [
                'name' => 'access_data',
                'label' => __('Access data'),
                'options' => $this->getOptions(),
                'multiple' => true,
                'required' => true,
            ] // In array mentioned configuration of element
        );

Meanwhile Please try the above example and If you have any Queries then please ask in the comment section below.

Thank you!

Contents

rencana pengembangan website



metode pengembangan website

jelaskan beberapa rencana untuk pengembangan website, proses pengembangan website, kekuatan dan kelemahan bisnis pengembangan website
, jasa pengembangan website, tahap pengembangan website, biaya pengembangan website

#Add #UISelect #search #filter #block #method #Admin #form #Magento

Tinggalkan Balasan

Alamat email Anda tidak akan dipublikasikan. Ruas yang wajib ditandai *