# uicore-elements/1.3.18/includes/widgets/contact-form.php

UiCore Elements – Free widgets and templates for Elementor, version 1.3.18. 1,401 lines.

- Page: https://pluginprobe.com/plugins/uicore-elements/1.3.18/code/includes/widgets/contact-form.php
- Raw: https://pluginprobe.com/plugins/uicore-elements/1.3.18/raw/includes/widgets/contact-form.php
- Modified: 2026-09-24T17:19:12+00:00

Line numbers below start at 1. Link to a line or a range by appending a fragment to the
page URL, for example `https://pluginprobe.com/plugins/uicore-elements/1.3.18/code/includes/widgets/contact-form.php#L10-L20`.

```php
<?php

namespace UiCoreElements;

use UiCoreElements\Helper;
use UiCoreElements\Utils\Contact_Form_Service;
use UiCoreElements\Utils\Form_Component;
use UiCoreElements\Utils\Newsletter_Services;

use Elementor\Controls_Manager;
use Elementor\Icons_Manager;
use Elementor\Utils;
use Elementor\Repeater;
use Elementor\Group_Control_Typography;
use Elementor\Group_Control_Border;
use Elementor\Core\Kits\Documents\Tabs\Global_Colors;
use Elementor\Core\Kits\Documents\Tabs\Global_Typography;


defined('ABSPATH') || exit();

/**
 * Contact Form
 *
 * @author Lucas Marini Falbo <lucas@uicore.co>
 * @since 1.0.5
 */

class ContactForm extends UiCoreWidget
{

    use Form_Component;

    public function get_name()
    {
        return 'uicore-contact-form';
    }

    public function get_title()
    {
        return __('Contact Form', 'uicore-elements');
    }

    public function get_icon()
    {
        return 'eicon-form-horizontal ui-e-widget';
    }
    public function get_categories()
    {
        return ['uicore'];
    }
    public function get_keywords()
    {
        return ['form', 'forms', 'contact', 'mail', 'send', 'field', 'button', 'recaptcha',];
    }
    public function get_styles()
    {
        return ['contact-form'];
    }
    public function get_scripts()
    {
        return [
            'contact-form',
            'recaptcha' => [
                'custom_condition' => $this->check_recaptcha_version('v2')
            ],
            'recaptcha-v3' => [
                'custom_condition' => $this->check_recaptcha_version('v3')
            ],
            'repeater-custom-key' => [
                'custom_condition' => $this->is_edit_mode()
            ]
        ];
    }
    public function has_widget_inner_wrapper(): bool
    {
        // TODO: remove after Optmized Markup experiment is merged to the core
        return ! \Elementor\Plugin::$instance->experiments->is_feature_active('e_optimized_markup');;
    }
    function check_recaptcha_version($version)
    {

        if ($this->is_edit_mode()) {
            return true;
        }
        $settings = $this->get_settings_for_display();
        foreach ($settings['form_fields'] as $field) {
            $version_to_check = $version === 'v2' ? 'recaptcha' : 'recaptcha_v3';
            if ($field['field_type'] === $version_to_check) {
                return true;
            }
        }
        return false;
    }

    // Helper Functions
    function get_field_types()
    {
        return [
            'text'      => esc_html__('Text', 'uicore-elements'),
            'email'     => esc_html__('Email', 'uicore-elements'),
            'textarea'  => esc_html__('Textarea', 'uicore-elements'),
            'url'       => esc_html__('URL', 'uicore-elements'),
            'tel'       => esc_html__('Tel', 'uicore-elements'),
            'radio'     => esc_html__('Radio', 'uicore-elements'),
            'select'    => esc_html__('Select', 'uicore-elements'),
            'checkbox'  => esc_html__('Checkbox', 'uicore-elements'),
            'acceptance' => esc_html__('Acceptance', 'uicore-elements'),
            'number'    => esc_html__('Number', 'uicore-elements'),
            'date'      => esc_html__('Date', 'uicore-elements'),
            'time'      => esc_html__('Time', 'uicore-elements'),
            'file'      => esc_html__('File Upload', 'uicore-elements'),
            'password'  => esc_html__('Password', 'uicore-elements'),
            'address'    => esc_html__('Honeypot', 'uicore-elements'),
            'recaptcha' => esc_html__('reCAPTCHA', 'uicore-elements'),
            'recaptcha_v3' => esc_html__('reCAPTCHA V3', 'uicore-elements'),
            'html'      => esc_html__('HTML', 'uicore-elements'),
            'hidden'    => esc_html__('Hidden', 'uicore-elements'),
        ];
    }

    function get_attribute_name($item)
    {
        return "form_fields[{$item['custom_id']}]";
    }
    function get_attribute_id($item)
    {
        return 'form-field-' . $item['custom_id'];
    }
    function add_required_attribute($element, $js_verication = false)
    {

        // Used for elements (eg: checkbox) that aren't natively supported by the browsers validations
        if ($js_verication) {
            $this->add_render_attribute($element, 'data-ui-e-required', 'true');
            return;
        }

        // Default method
        $this->add_render_attribute($element, 'required', 'required');
        $this->add_render_attribute($element, 'aria-required', 'true');
    }

    // Field Render Functions
    function build_honeypot_field($item, $item_index)
    {
        $this->add_render_attribute('honeypot' . $item_index, [
            'class' => [
                'ui-e-field',
                'ui-e-h-p',
                esc_attr($item['css_classes']),
            ],
            'name' => 'ui-e-h-p',
            'id' => 'ui-e-h-p',
            'autocomplete' => 'off',
        ]);

        if ($item['placeholder']) {
            $this->add_render_attribute('honeypot' . $item_index, 'placeholder', $item['placeholder']);
        }

        if ($item['required']) {
            $this->add_required_attribute('honeypot' . $item_index);
        }

        $value = empty($item['field_value']) ? '' : $item['field_value'];

        return '<input ' . $this->get_render_attribute_string('honeypot' . $item_index) . ' tabindex="-1">' . esc_html($value) . '</input>';
    }
    function build_textarea_field($item, $item_index)
    {
        $this->add_render_attribute('textarea' . $item_index, [
            'class' => [
                'ui-e-field',
                esc_attr($item['css_classes']),
            ],
            'name' => $this->get_attribute_name($item),
            'id' => $this->get_attribute_id($item),
            'rows' => $item['rows'],
        ]);

        if ($item['placeholder']) {
            $this->add_render_attribute('textarea' . $item_index, 'placeholder', $item['placeholder']);
        }

        if ($item['required']) {
            $this->add_required_attribute('textarea' . $item_index);
        }

        $value = empty($item['field_value']) ? '' : $item['field_value'];

        return '<textarea ' . $this->get_render_attribute_string('textarea' . $item_index) . '>' . esc_textarea($value) . '</textarea>';
    }
    function build_select_field($item, $i)
    {
        $this->add_render_attribute(
            [
                'select-wrapper' . $i => [
                    'class' => [
                        'ui-e-field',
                        'ui-e-field-select',
                        'ui-e-field-subgroup',
                        esc_attr($item['css_classes']),
                    ],
                ],
                'select' . $i => [
                    'name' => $this->get_attribute_name($item) . (! empty($item['allow_multiple']) ? '[]' : ''),
                    'id' => $this->get_attribute_id($item),
                    'class' => [
                        'ui-e-field-textual',
                    ],
                ],
            ]
        );

        if ($item['required']) {
            $this->add_required_attribute('select' . $i);
        }

        if ($item['allow_multiple']) {
            $this->add_render_attribute('select' . $i, 'multiple');
            if (! empty($item['select_size'])) {
                $this->add_render_attribute('select' . $i, 'size', $item['select_size']);
            }
        }

        $options = preg_split("/\\r\\n|\\r|\\n/", $item['field_options']);

        if (! $options) {
            return '';
        }

        ob_start();
?>
        <div <?php $this->print_render_attribute_string('select-wrapper' . $i); ?>>
            <select <?php $this->print_render_attribute_string('select' . $i); ?>>
                <?php
                foreach ($options as $key => $option) {
                    $option_id = $item['custom_id'] . $key;
                    $option_value = esc_attr($option);
                    $option_label = esc_html($option);

                    if (false !== strpos($option, '|')) {
                        list($label, $value) = explode('|', $option);
                        $option_value = esc_attr($value);
                        $option_label = esc_html($label);
                    }

                    $this->add_render_attribute($option_id, 'value', $option_value);

                    // Support multiple selected values
                    if (! empty($item['field_value']) && in_array($option_value, explode(',', $item['field_value']))) {
                        $this->add_render_attribute($option_id, 'selected', 'selected');
                    } ?>
                    <option <?php $this->print_render_attribute_string($option_id); ?>><?php
                                                                                        // PHPCS - $option_label is already escaped
                                                                                        echo $option_label; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                                                                        ?></option>
                <?php } ?>
            </select>
        </div>
    <?php

        $select = ob_get_clean();
        return $select;
    }
    function build_radio_checkbox_field($item, $item_index, $type)
    {
        $options = preg_split("/\\r\\n|\\r|\\n/", $item['field_options']);
        $html = '';
        if ($options) {
            $html .= '<div class="ui-e-field-subgroup ' . esc_attr($item['css_classes']) . ' ' . esc_attr($item['inline_list']) . '">';
            foreach ($options as $key => $option) {
                $element_id = $item['custom_id'] . $key;
                $html_id = $this->get_attribute_id($item) . '-' . $key;
                $option_label = $option;
                $option_value = $option;
                if (false !== strpos($option, '|')) {
                    list($option_label, $option_value) = explode('|', $option);
                }

                $this->add_render_attribute(
                    $element_id,
                    [
                        'type' => $type,
                        'value' => $option_value,
                        'id' => $html_id,
                        'name' => $this->get_attribute_name($item) . (('checkbox' === $type && count($options) > 1) ? '[]' : ''),
                    ]
                );

                if ($item['required']) {
                    $this->add_required_attribute($element_id, true);
                }

                if (! empty($item['field_value']) && $option_value === $item['field_value']) {
                    $this->add_render_attribute($element_id, 'checked', 'checked');
                }

                if ($item['required'] && 'radio' === $type) {
                    $this->add_required_attribute($element_id);
                }

                $html .= '<span class="ui-e-field-option">';
                $html .= '<input ' . $this->get_render_attribute_string($element_id) . '>';
                $html .= '<label for="' . $html_id . '">';
                $html .= esc_html($option_label);
                $html .= '</label></span>';
            }
            $html .= '</div>';
        }

        return $html;
    }
    function build_acceptance_field($item, $item_index)
    {
        $text = '';
        $this->add_render_attribute('input' . $item_index, 'class', 'ui-e-acceptance-field');
        $this->add_render_attribute('input' . $item_index, 'type', 'checkbox', true);

        if (! empty($item['acceptance_text'])) {
            $text = '<label for="' . $this->get_attribute_id($item) . '">' . Helper::esc_string($item['acceptance_text']) . '</label>';
        }

        if (! empty($item['checked_by_default'])) {
            $this->add_render_attribute('input' . $item_index, 'checked', 'checked');
        }

    ?>
        <div class="ui-e-field-subgroup <?php echo esc_attr($item['css_classes']); ?>">
            <input <?php $this->print_render_attribute_string('input' . $item_index); ?>>
            <?php // PHPCS - the variables $text is safe.
            echo $text; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
            ?>
        </div>
    <?php
    }
    function form_fields_render_attributes($i, $instance, $item)
    {
        $this->add_render_attribute(
            [
                'field-group' . $i => [
                    'class' => [
                        'ui-e-field-type-' . $item['field_type'],
                        'ui-e-field-group',
                        'elementor-column',
                        'ui-e-field-group-' . $item['custom_id'],
                    ],
                ],
                'input' . $i => [
                    'type' => $item['field_type'],
                    'name' => $this->get_attribute_name($item),
                    'id' => $this->get_attribute_id($item),
                    'class' => [
                        'ui-e-field',
                        empty($item['css_classes']) ? '' : esc_attr($item['css_classes']),
                    ],
                ],
                'label' . $i => [
                    'for' => $this->get_attribute_id($item),
                    'class' => 'ui-e-label',
                ],
            ]
        );

        if (empty($item['width'])) {
            $item['width'] = '100';
        }

        $this->add_render_attribute('field-group' . $i, 'class', 'elementor-col-' . $item['width']);

        if (! empty($item['width_tablet'])) {
            $this->add_render_attribute('field-group' . $i, 'class', 'elementor-md-' . $item['width_tablet']);
        }

        if ($item['allow_multiple']) {
            $this->add_render_attribute('field-group' . $i, 'class', 'ui-e-field-type-' . $item['field_type'] . '-multiple');
        }

        if (! empty($item['width_mobile'])) {
            $this->add_render_attribute('field-group' . $i, 'class', 'elementor-sm-' . $item['width_mobile']);
        }

        // Allow zero as placeholder.
        if (! Utils::is_empty($item['placeholder'])) {
            $this->add_render_attribute('input' . $i, 'placeholder', $item['placeholder']);
        }

        if (! empty($item['field_value'])) {
            $this->add_render_attribute('input' . $i, 'value', $item['field_value']);
        }

        if (! $instance['show_labels']) {
            $this->add_render_attribute('label' . $i, 'class', 'elementor-screen-only');
        }

        if (! empty($item['required'])) {
            $class = '';
            if (! empty($instance['mark_required'])) {
                $class .= ' ui-e-required';
            }
            $this->add_render_attribute('field-group' . $i, 'class', $class);
            $this->add_required_attribute('input' . $i);
        }
    }

    protected function register_controls()
    {

        // Content Controls
        // Repeater Controls used by `form_fields` control
        $repeater = new Repeater();
        $repeater->start_controls_tabs('form_fields_tabs');

        $repeater->start_controls_tab(
            'form_fields_content_tab',
            [
                'label' => esc_html__('Content', 'uicore-elements'),
            ]
        );

        $repeater->add_control(
            'field_type',
            [
                'label' => esc_html__('Type', 'uicore-elements'),
                'type' => Controls_Manager::SELECT,
                'options' => $this->get_field_types(),
                'default' => 'text',
            ]
        );
        $repeater->add_control(
            'field_label',
            [
                'label' => esc_html__('Label', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => '',
                'dynamic' => [
                    'active' => true,
                ],
            ]
        );
        $repeater->add_control(
            'placeholder',
            [
                'label' => esc_html__('Placeholder', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => '',
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'operator' => 'in',
                            'value' => [
                                'tel',
                                'text',
                                'email',
                                'textarea',
                                'number',
                                'url',
                                'password',
                            ],
                        ],
                    ],
                ],
                'dynamic' => [
                    'active' => true,
                ],
            ]
        );
        $repeater->add_control(
            'required',
            [
                'label' => esc_html__('Required', 'uicore-elements'),
                'type' => Controls_Manager::SWITCHER,
                'return_value' => 'true',
                'default' => '',
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'operator' => '!in',
                            'value' => [
                                'recaptcha',
                                'recaptcha_v3',
                                'hidden',
                                'html',
                            ],
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'field_options',
            [
                'label' => esc_html__('Options', 'uicore-elements'),
                'type' => Controls_Manager::TEXTAREA,
                'default' => '',
                'description' => esc_html__('Enter each option in a separate line. To differentiate between label and value, separate them with a pipe char ("|"). For example: First Name|f_name', 'uicore-elements'),
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'operator' => 'in',
                            'value' => [
                                'select',
                                'checkbox',
                                'radio',
                            ],
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'allow_multiple',
            [
                'label' => esc_html__('Multiple Selection', 'uicore-elements'),
                'type' => Controls_Manager::SWITCHER,
                'return_value' => 'true',
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'value' => 'select',
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'select_size',
            [
                'label' => esc_html__('Rows', 'uicore-elements'),
                'type' => Controls_Manager::NUMBER,
                'min' => 2,
                'step' => 1,
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'value' => 'select',
                        ],
                        [
                            'name' => 'allow_multiple',
                            'value' => 'true',
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'inline_list',
            [
                'label' => esc_html__('Inline List', 'uicore-elements'),
                'type' => Controls_Manager::SWITCHER,
                'return_value' => 'ui-e-subgroup-inline',
                'default' => '',
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'operator' => 'in',
                            'value' => [
                                'checkbox',
                                'radio',
                            ],
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'field_html',
            [
                'label' => esc_html__('HTML', 'uicore-elements'),
                'type' => Controls_Manager::TEXTAREA,
                'dynamic' => [
                    'active' => true,
                ],
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'value' => 'html',
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'acceptance_text',
            [
                'label' => esc_html__('Acceptance Text', 'uicore-elements'),
                'type' => Controls_Manager::TEXTAREA,
                'condition' => [
                    'field_type' => 'acceptance',
                ],
            ],
        );
        $repeater->add_control(
            'checked_by_default',
            [
                'label' => esc_html__('Checked by Default', 'uicore-elements'),
                'type' => Controls_Manager::SWITCHER,
                'condition' => [
                    'field_type' => 'acceptance',
                ],
            ],
        );
        $repeater->add_responsive_control(
            'width',
            [
                'label' => esc_html__('Column Width', 'uicore-elements'),
                'type' => Controls_Manager::SELECT,
                'options' => [
                    '' => esc_html__('Default', 'uicore-elements'),
                    '100' => '100%',
                    '80' => '80%',
                    '75' => '75%',
                    '70' => '70%',
                    '66' => '66%',
                    '60' => '60%',
                    '50' => '50%',
                    '40' => '40%',
                    '33' => '33%',
                    '30' => '30%',
                    '25' => '25%',
                    '20' => '20%',
                ],
                'default' => '100',
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'operator' => '!in',
                            'value' => [
                                'hidden',
                                'recaptcha',
                                'recaptcha_v3'
                            ],
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'rows',
            [
                'label' => esc_html__('Rows', 'uicore-elements'),
                'type' => Controls_Manager::NUMBER,
                'default' => 4,
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'value' => 'textarea',
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'recaptcha_hide',
            [
                'label' => esc_html__('Badge', 'uicore-elements'),
                'type' => Controls_Manager::SELECT,
                'default' => 'hidden',
                'options' => [
                    'hidden' => esc_html__('Hidden', 'uicore-elements'),
                    'visible' => esc_html__('Visible', 'uicore-elements')
                ],
                'condition' => [
                    'field_type' => 'recaptcha_v3',
                ],
                'selectors' => [
                    '.grecaptcha-badge' => 'visibility: {{VALUE}};',
                ],
            ]
        );
        $recaptcha_keys = (!get_option('uicore_elements_recaptcha_secret_key') && !get_option('uicore_elements_recaptcha_site_key')) ? true : false;  // Check if recaptcha API keys were set
        $repeater->add_control(
            'recaptcha_warning',
            [
                'type' => Controls_Manager::ALERT,
                'alert_type' => 'warning',
                'dismissible' => false,
                'heading' => esc_html__("You haven't set your reCAPTCHA API keys yet.", 'uicore-elements'),
                'content' => Helper::get_admin_settings_url(esc_html__("Click here to configure your API keys.", 'uicore-elements')),
                'condition' => [
                    'field_type' => $recaptcha_keys ? ['recaptcha', 'recaptcha_v3'] : [],
                ]
            ]
        );

        $repeater->end_controls_tab();

        $repeater->start_controls_tab(
            'form_fields_advanced_tab',
            [
                'label' => esc_html__('Advanced', 'uicore-elements'),
                'condition' => [
                    'field_type!' => ['html', 'address'],
                ],
            ]
        );

        $repeater->add_control(
            'field_value',
            [
                'label' => esc_html__('Default Value', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => '',
                'dynamic' => [
                    'active' => true,
                ],
                'ai' => [
                    'active' => false,
                ],
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'field_type',
                            'operator' => 'in',
                            'value' => [
                                'text',
                                'email',
                                'textarea',
                                'url',
                                'tel',
                                'radio',
                                'select',
                                'number',
                                'date',
                                'time',
                                'hidden',
                            ],
                        ],
                    ],
                ],
            ]
        );
        $repeater->add_control(
            'custom_id',
            [
                'label' => esc_html__('ID', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'description' => esc_html__('Please make sure the ID is unique and not used elsewhere in this form. This field allows `A-z 0-9` & underscore chars without spaces.', 'uicore-elements'),
                'render_type' => 'none',
                'required' => true,
                'dynamic' => [
                    'active' => true,
                ],
                'ai' => [
                    'active' => false,
                ],
            ]
        );
        $repeater->add_control(
            'css_classes',
            [
                'label' => esc_html__('Custom Class', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => '',
                'ai' => [
                    'active' => false,
                ],
                'placeholder' => esc_html__('e.g: my-class', 'uicore-elements'),
            ]
        );
        $shortcode_template = '{{ view.container.settings.get( \'custom_id\' ) }}';
        $repeater->add_control(
            'shortcode',
            [
                'label' => esc_html__('Shortcode', 'uicore-elements'),
                'type' => Controls_Manager::RAW_HTML,
                'classes' => 'forms-field-shortcode',
                'raw' => '<input class="elementor-form-field-shortcode" value=\'[field id="' . $shortcode_template . '"]\' readonly />',
                'label_block' => false,
            ]
        );

        $repeater->end_controls_tab();

        $repeater->end_controls_tabs();

        $this->start_controls_section(
            'section_form_fields',
            [
                'label' => esc_html__('Form Fields', 'uicore-elements'),
            ]
        );


        $this->add_control(
            'form_name',
            [
                'label' => esc_html__('Form Name', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => esc_html__('New Form', 'uicore-elements'),
                'placeholder' => esc_html__('Form Name', 'uicore-elements'),
            ]
        );
        $this->add_control(
            'form_fields',
            [
                'type' => Controls_Manager::REPEATER,
                'fields' => $repeater->get_controls(),
                'default' => [
                    [
                        'custom_id' => 'name',
                        'field_type' => 'text',
                        'field_label' => esc_html__('Name', 'uicore-elements'),
                        'placeholder' => esc_html__('Name', 'uicore-elements'),
                        'width' => '100',
                        'dynamic' => [
                            'active' => true,
                        ],
                    ],
                    [
                        'custom_id' => 'email',
                        'field_type' => 'email',
                        'required' => 'true',
                        'field_label' => esc_html__('Email', 'uicore-elements'),
                        'placeholder' => esc_html__('Email', 'uicore-elements'),
                        'width' => '100',
                    ],
                    [
                        'custom_id' => 'address',
                        'field_type' => 'address',
                        'field_label' => esc_html__('address (honeypot)', 'uicore-elements'),
                        'placeholder' => esc_html__('address', 'uicore-elements'),
                        'width' => '100',
                    ],
                    [
                        'custom_id' => 'message',
                        'field_type' => 'textarea',
                        'field_label' => esc_html__('Message', 'uicore-elements'),
                        'placeholder' => esc_html__('Message', 'uicore-elements'),
                        'width' => '100',
                    ],
                ],
                'title_field' => '{{ field_label }}',
            ]
        );
        $this->add_control(
            'show_labels',
            [
                'label' => esc_html__('Label', 'uicore-elements'),
                'type' => Controls_Manager::SWITCHER,
                'label_on' => esc_html__('Show', 'uicore-elements'),
                'label_off' => esc_html__('Hide', 'uicore-elements'),
                'return_value' => 'true',
                'default' => 'true',
                'separator' => 'before',
            ]
        );
        $this->add_control(
            'mark_required',
            [
                'label' => esc_html__('Required Mark', 'uicore-elements'),
                'type' => Controls_Manager::SWITCHER,
                'label_on' => esc_html__('Show', 'uicore-elements'),
                'label_off' => esc_html__('Hide', 'uicore-elements'),
                'default' => '',
                'render_type' => 'template',
                'condition' => [
                    'show_labels!' => '',
                ],
            ]
        );

        $this->end_controls_section();

        $this->start_controls_section(
            'section_buttons',
            [
                'label' => esc_html__('Button', 'uicore-elements'),
            ]
        );

        $this->add_responsive_control(
            'button_width',
            [
                'label' => esc_html__('Column Width', 'uicore-elements'),
                'type' => Controls_Manager::SELECT,
                'options' => [
                    '' => esc_html__('Default', 'uicore-elements'),
                    '100' => '100%',
                    '80' => '80%',
                    '75' => '75%',
                    '70' => '70%',
                    '66' => '66%',
                    '60' => '60%',
                    '50' => '50%',
                    '40' => '40%',
                    '33' => '33%',
                    '30' => '30%',
                    '25' => '25%',
                    '20' => '20%',
                ],
                'default' => '100',
            ]
        );
        $this->add_responsive_control(
            'button_align',
            [
                'label' => esc_html__('Alignment', 'uicore-elements'),
                'type' => Controls_Manager::CHOOSE,
                'options' => [
                    'left' => [
                        'title' => esc_html__('Left', 'uicore-elements'),
                        'icon' => 'eicon-text-align-left',
                    ],
                    'center' => [
                        'title' => esc_html__('Center', 'uicore-elements'),
                        'icon' => 'eicon-text-align-center',
                    ],
                    'right' => [
                        'title' => esc_html__('Right', 'uicore-elements'),
                        'icon' => 'eicon-text-align-right',
                    ],
                    'stretch' => [
                        'title' => esc_html__('Justified', 'uicore-elements'),
                        'icon' => 'eicon-text-align-justify',
                    ],
                ],
                'default' => 'stretch',
                'prefix_class' => 'ui-e-submit-align-%s-',
            ]
        );
        $this->add_control(
            'button_text',
            [
                'label' => esc_html__('Submit', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => esc_html__('Send', 'uicore-elements'),
                'placeholder' => esc_html__('Send', 'uicore-elements'),
                'dynamic' => [
                    'active' => true,
                ],
                'ai' => [
                    'active' => false,
                ],
            ]
        );
        $this->add_control(
            'selected_button_icon',
            [
                'label' => esc_html__('Icon', 'uicore-elements'),
                'type' => Controls_Manager::ICONS,
                'skin' => 'inline',
                'label_block' => false,
            ]
        );
        $this->add_control(
            'button_icon_align',
            [
                'label' => esc_html__('Icon Position', 'uicore-elements'),
                'type' => Controls_Manager::SELECT,
                'default' => 'left',
                'options' => [
                    'left' => esc_html__('Before', 'uicore-elements'),
                    'right' => esc_html__('After', 'uicore-elements'),
                ],
                'condition' => [
                    'selected_button_icon[value]!' => '',
                ],
            ]
        );
        $this->add_control(
            'button_icon_indent',
            [
                'label' => esc_html__('Icon Spacing', 'uicore-elements'),
                'type' => Controls_Manager::SLIDER,
                'size_units' => ['px', 'em', 'rem', 'custom'],
                'range' => [
                    'px' => [
                        'max' => 100,
                    ],
                    'em' => [
                        'max' => 10,
                    ],
                    'rem' => [
                        'max' => 10,
                    ],
                ],
                'condition' => [
                    'selected_button_icon[value]!' => '',
                ],
                'selectors' => [
                    '{{WRAPPER}} .elementor-button .ui-e-align-right' => 'margin-left: {{SIZE}}{{UNIT}};',
                    '{{WRAPPER}} .elementor-button .ui-e-align-left' => 'margin-right: {{SIZE}}{{UNIT}};',
                ],
            ]
        );
        $this->add_control(
            'button_css_id',
            [
                'label' => esc_html__('Button ID', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => '',
                'ai' => [
                    'active' => false,
                ],
                'title' => esc_html__('Add your custom id WITHOUT the Pound key. e.g: my-id', 'uicore-elements'),
                'description' => esc_html__('Please make sure the ID is unique and not used elsewhere on the page this form is displayed. This field allows `A-z 0-9` & underscore chars without spaces.', 'uicore-elements'),
                'separator' => 'before',
                'dynamic' => [
                    'active' => true,
                ],
            ]
        );


        $this->end_controls_section();

        $this->TRAIT_register_submit_actions_controls(Contact_Form_Service::get_form_submit_options());

        // Submit sections
        $this->start_controls_section(
            'section_email',
            [
                'label' => esc_html__('Email', 'uicore-elements'),
                'condition' => [
                    'submit_actions' => 'email',
                ],
            ]
        );

        $this->TRAIT_register_submit_email_controls($this);

        $this->end_controls_section();

        $this->start_controls_section(
            'section_email_2',
            [
                'label' => esc_html__('Email 2', 'uicore-elements'),
                'condition' => [
                    'submit_actions' => 'email_2',
                ],
            ]
        );

        $this->TRAIT_register_submit_email_controls($this, '_2');

        $this->end_controls_section();

        $this->TRAIT_register_submit_redirect_controls();
        $this->TRAIT_register_submit_popup_controls($this);
        $this->TRAIT_register_submit_webhook_controls();
        $this->TRAIT_register_submit_newsletter_services_controls(Newsletter_Services::get_services_list('keys'), true);
        $default_messages = Contact_Form_Service::get_default_messages();
        $this->TRAIT_register_additional_controls($default_messages);

        $this->TRAIT_register_all_form_style_controls();

        // Custom Fields additional Controls injection
        $this->start_injection([
            'of' => 'redirect_message',
            'at' => 'before',
        ]);
        $this->add_control(
            'required_fields_message',
            [
                'label' => esc_html__('Required Fields', 'uicore-elements'),
                'type' => Controls_Manager::TEXT,
                'default' => $default_messages['required'],
                'placeholder' => $default_messages['required'],
                'label_block' => true,
                'conditions' => [
                    'terms' => [
                        [
                            'name' => 'custom_messages',
                            'operator' => '!=',
                            'value' => '',
                        ],
                    ],
                ],
                'render_type' => 'none',
                'dynamic' => [
                    'active' => true,
                ],
            ]
        );
        $this->end_injection();

        // Specific Form style controls
        $this->start_injection([
            'of' => 'form_styles_component_divider',
            'at' => 'after',
        ]);

        $this->add_control(
            'heading_html',
            [
                'label' => esc_html__('HTML Field', 'uicore-elements'),
                'type' => Controls_Manager::HEADING,
            ]
        );
        $this->add_control(
            'html_spacing',
            [
                'label' => esc_html__('Spacing', 'uicore-elements'),
                'type' => Controls_Manager::SLIDER,
                'size_units' => ['px', 'em', 'rem', 'custom'],
                'default' => [
                    'size' => 0,
                ],
                'range' => [
                    'px' => [
                        'max' => 60,
                    ],
                    'em' => [
                        'max' => 6,
                    ],
                    'rem' => [
                        'max' => 6,
                    ],
                ],
                'selectors' => [
                    '{{WRAPPER}} .ui-e-field-type-html' => 'padding-bottom: {{SIZE}}{{UNIT}};',
                ],
            ]
        );
        $this->add_control(
            'html_color',
            [
                'label' => esc_html__('Color', 'uicore-elements'),
                'type' => Controls_Manager::COLOR,
                'selectors' => [
                    '{{WRAPPER}} .ui-e-field-type-html' => 'color: {{VALUE}};',
                ],
            ]
        );
        $this->add_group_control(
            Group_Control_Typography::get_type(),
            [
                'name' => 'html_typography',
                'selector' => '{{WRAPPER}} .ui-e-field-type-html',
                'global' => [
                    'default' => Global_Typography::TYPOGRAPHY_TEXT,
                ],
            ]
        );

        $this->add_control(
            'heading_file',
            [
                'label' => esc_html__('Upload File Field', 'uicore-elements'),
                'type' => Controls_Manager::HEADING,
                'separator' => 'before',
            ]
        );
        $this->add_control(
            'file_color',
            [
                'label' => esc_html__('Color', 'uicore-elements'),
                'type' => Controls_Manager::COLOR,
                'selectors' => [
                    '{{WRAPPER}} .ui-e-field-type-file input.ui-e-field' => 'color: {{VALUE}};',
                ],
                'default' => 'var(--e-global-color-uicore_body)',

            ]
        );
        $this->end_injection();
    }
    function recaptcha_js()
    {
    ?>
        <script>
            window.uicore_elements_recaptcha = '<?php echo esc_html(get_option('uicore_elements_recaptcha_site_key')); ?>';
        </script>
    <?php
    }

    protected function render()
    {

        $instance = $this->get_settings_for_display();
        $is_recaptcha_required = false;

        // Save widget settings so form API can retrieve them
        set_transient('ui_e_form_widget_settings_' . $this->get_id(), $instance, DAY_IN_SECONDS);

        // Render Form Atts
        $this->add_render_attribute(
            [
                'wrapper' => [
                    'class' => [
                        'ui-e-fields-wrp',
                    ],
                ],
                'submit-group' => [
                    'class' => [
                        'ui-e-field-group',
                        'elementor-column',
                        'ui-e-field-type-submit',
                    ],
                ],
                'button' => [
                    'class' => 'elementor-button',
                ],
                'icon-align' => [
                    'class' => [
                        empty($instance['button_icon_align']) ? '' : 'ui-e-icon ui-e-align-' . $instance['button_icon_align'],
                    ],
                ],
            ]
        );

        // Fallback for empty control values
        if (empty($instance['button_width'])) {
            $instance['button_width'] = '100';
        }

        // Button atts
        $this->add_render_attribute('submit-group', 'class', 'elementor-col-' . $instance['button_width'] . ' e-form__buttons');

        if (! empty($instance['button_width_tablet'])) {
            $this->add_render_attribute('submit-group', 'class', 'elementor-md-' . $instance['button_width_tablet']);
        }
        if (! empty($instance['button_width_mobile'])) {
            $this->add_render_attribute('submit-group', 'class', 'elementor-sm-' . $instance['button_width_mobile']);
        }
        if ($instance['button_hover_animation']) {
            $this->add_render_attribute('button', 'class', 'elementor-animation-' . $instance['button_hover_animation']);
        }

        // Form atts
        if (! empty($instance['form_id'])) {
            $this->add_render_attribute('form', 'id', $instance['form_id']);
        }
        if (! empty($instance['form_name'])) {
            $this->add_render_attribute('form', 'name', $instance['form_name']);
        }
        if ('no' === $instance['form_validation']) {
            $this->add_render_attribute('form', 'novalidate');
        }
        if (! empty($instance['button_css_id'])) {
            $this->add_render_attribute('button', 'id', $instance['button_css_id']);
        }

        $referer_title = trim(wp_title('', false));
        if (! $referer_title && is_home()) {
            $referer_title = get_option('blogname');
        }

        // Get default messages
        $messages = Contact_Form_Service::get_default_messages();

        // Set frontend validation message
        $front_msg_required = isset($instance['required_fields_message'])
            ? $instance['required_fields_message']
            : $messages['required'];
    ?>

        <form class="ui-e-form" method="post" <?php $this->print_render_attribute_string('form'); ?>>

            <input type="hidden" name="post_id" value="<?php echo esc_attr(get_the_ID()); ?>" />
            <input type="hidden" name="widget_type" value="contact-form">

            <input type="hidden" name="required_fields_message" value="<?php echo esc_html($front_msg_required); ?>">

            <div <?php $this->print_render_attribute_string('wrapper'); ?>>

                <?php foreach ($instance['form_fields'] as $item_index => $item) :
                    $this->form_fields_render_attributes($item_index, $instance, $item);

                    $field_type = $item['field_type'];

                    if ($field_type === 'recaptcha' || $field_type === 'recaptcha_v3') {
                        $is_recaptcha_required = true;
                    }

                    $print_label = ! in_array($item['field_type'], ['hidden', 'html'], true);
                ?>

                    <div <?php $this->print_render_attribute_string('field-group' . $item_index); ?>>
                        <?php
                        // Print label (excepts if recaptcha)
                        if ($print_label && $item['field_label'] && $item['field_type'] !== 'recaptcha' && $item['field_type'] !== 'recaptcha_v3') {
                        ?>
                            <label <?php $this->print_render_attribute_string('label' . $item_index); ?>>
                                <?php // PHPCS - the variable $item['field_label'] is safe.
                                echo Helper::esc_string($item['field_label']); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                ?>
                            </label>
                            <?php
                        }

                        // Print field
                        switch ($item['field_type']):
                            case 'html':
                                echo wp_kses_post(do_shortcode($item['field_html']));
                                break;

                            case 'textarea':
                                // PHPCS - the method build_textarea_field is safe.
                                echo $this->build_textarea_field($item, $item_index); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                break;

                            case 'select':
                                // PHPCS - the method build_select_field is safe.
                                echo $this->build_select_field($item, $item_index); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                break;

                            case 'acceptance':
                                // PHPCS - the method build_select_field is safe.
                                $this->build_acceptance_field($item, $item_index); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                break;

                            case 'radio':
                            case 'checkbox':
                                // PHPCS - the method build_radio_checkbox_field is safe.
                                echo $this->build_radio_checkbox_field($item, $item_index, $item['field_type']); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                break;

                            case 'address': // is actually honeypot
                                // PHPCS - the method build_honeypot_field is safe.
                                echo $this->build_honeypot_field($item, $item_index); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
                                break;

                            case 'recaptcha':
                                // get widget ID
                                echo '<input type="hidden" name="recaptcha"/>  <div id="ui-e-recaptcha-' . esc_attr($this->get_ID()) . '"></div>';
                                break;

                            case 'recaptcha_v3':
                                echo '<input type="hidden" name="recaptcha_v3"/>';
                                break;

                            // All other cases are covered by the add_render_atribute()
                            default:
                                $this->add_render_attribute('input' . $item_index, 'class', 'ui-e-field-textual');
                            ?>
                                <input size="1" <?php $this->print_render_attribute_string('input' . $item_index); ?>>
                        <?php
                                break;

                        endswitch;
                        ?>
                    </div>

                <?php endforeach; ?>

                <div <?php $this->print_render_attribute_string('submit-group'); ?>>
                    <button type="submit" <?php $this->print_render_attribute_string('button'); ?>>
                        <span <?php $this->print_render_attribute_string('content-wrapper'); ?>>
                            <?php if (! empty($instance['button_icon']) || ! empty($instance['selected_button_icon'])) : ?>
                                <span <?php $this->print_render_attribute_string('icon-align'); ?>>
                                    <?php Icons_Manager::render_icon($instance['selected_button_icon'], ['aria-hidden' => 'true']); ?>
                                    <?php if (empty($instance['button_text'])) : ?>
                                        <span class="elementor-screen-only"><?php echo esc_html__('Submit', 'uicore-elements'); ?></span>
                                    <?php endif; ?>
                                </span>
                            <?php endif; ?>
                            <?php if (! empty($instance['button_text'])) : ?>
                                <span class="ui-e-text"><?php $this->print_unescaped_setting('button_text'); ?></span>
                            <?php endif; ?>
                        </span>
                    </button>
                </div>

            </div>

            <div class="ui-e-message <?php echo $this->is_edit_mode() ? 'elementor-hidden' : ''; ?>">
                <?php if ($this->is_edit_mode()) :
                    // Get custom messages if set, else use default
                    $success = isset($instance['success_message'])
                        ? $instance['success_message']
                        : $messages['success'];
                    $error = isset($instance['error_message'])
                        ? $instance['error_message']
                        : $messages['error'];
                ?>
                    <span class="success"> <?php echo esc_html($success); ?> </span> <br>
                    <span class="error"> <?php echo esc_html($error); ?> </span>
                <?php endif; ?>
            </div>
        </form>
        <?php

        //add js to footer if recaptcha is enabled
        if ($is_recaptcha_required) {
            add_action('wp_footer', [$this, 'recaptcha_js'], 999);
        }

        // Add frontend validation messages to js var
        ?>
        <script>
            window.ui_e_form_validation_messages = <?php echo json_encode([
                                                        'required_fields' => esc_html($front_msg_required),
                                                    ]); ?>;
        </script>
<?php
    }
}
\Elementor\Plugin::instance()->widgets_manager->register(new ContactForm());

```
