- What is Elementor
- What Is a Elementor Widget?
- Creating Custom Widget
- Registering Widgets
- Add ajax code to fetch image
- Register script to execute Ajax code
- Creating Widget functionality
- Download Full Code Plugin
What is Elementor
Elementor is the leading WordPress website page builder that give you ability to successfully build clean, professional, pixel-accurate websites. With an Elementor Widget intuitive drag and drop interface, you get complete control to build any type of website, without writing a single line of code.
What Is a Elementor Widget?
Elementor Widget refers to a small GUI application that is used for completing a specific task. Elementor have lots of useful widgets in the widgets panel. These widgets are divided into categories.
Creating Custom Widget
We will create a simple Elementor Widget that adds widgets to Elementor left side panel . it add title and image which load using ajax. below is folder and file structure.
elementor-module/ | ├─ widgets/ | ├─ image-module-widget.php | ├─ js/ | ├─ module_img_script.js | ├─ img/ | ├─ loading-icon.gif | └─ elementor-module.php
Create folder “elementor-module” in folder plugins in wordpress. next create file “elementor-module.php” in folder “elementor-module” and add below code.
plugins/elementor-module/elementor-module.php
<?php /** * Plugin Name: Elementor Module * Description: Simple image load with ajax widgets for Elementor. * Version: 1.0.0 * Author: Elementor Module Developer * Author URI: https://webdav.in * Text Domain: elementor-module */ function register_image_module_widget($widgets_manager) { require_once(__DIR__ . '/widgets/image-module-widget.php'); $widgets_manager->register(new \Elementor_Image_Module_Widget()); } add_action('elementor/widgets/register', 'register_image_module_widget'); add_action("wp_ajax_module_img_fetch", "module_img_fetch"); add_action("wp_ajax_nopriv_module_img_fetch", "module_img_fetch"); function module_img_fetch() { if (!wp_verify_nonce($_REQUEST['nonce'], "module_img_fetch_nonce")) { exit("No naughty business please"); } $img_ids = $_REQUEST['img_id']; $module_img_size = $_REQUEST['module_img_size']; $i = 0; foreach ($img_ids as $img_id) { $response[$img_id] = wp_get_attachment_image($img_id, $module_img_size[$i]); $i++; } wp_send_json($response); die(); } add_action('init', 'my_script_enqueuer'); function my_script_enqueuer() { wp_enqueue_script('jquery'); wp_enqueue_script('module_img_fetch_script', plugin_dir_url(__FILE__) . 'js/module_img_script.js', array('jquery')); wp_localize_script('module_img_fetch_script', 'moduleFetchAjax', array('ajaxurl' => admin_url('admin-ajax.php'), 'security' => wp_create_nonce('module_img_fetch_nonce'))); wp_enqueue_script('module_img_fetch_script'); }
Registering Widgets
To register new widgets use the following code:
function register_image_module_widget($widgets_manager) { require_once(__DIR__ . '/widgets/image-module-widget.php'); $widgets_manager->register(new \Elementor_Image_Module_Widget()); } add_action('elementor/widgets/register', 'register_image_module_widget');
We just connect to the elementor/widgets/register action which gives access to the widgets manager as a parameter. We can use the widgets manager to add new widgets using the register() method with the widget instance
Add ajax code to fetch image
add_action("wp_ajax_module_img_fetch", "module_img_fetch_func"); add_action("wp_ajax_nopriv_module_img_fetch", "module_img_fetch_func"); function module_img_fetch_func() { if (!wp_verify_nonce($_REQUEST['nonce'], "module_img_fetch_nonce")) { exit("No naughty business please"); } $img_ids = $_REQUEST['img_id']; $module_img_size = $_REQUEST['module_img_size']; $i = 0; foreach ($img_ids as $img_id) { $response[$img_id] = wp_get_attachment_image($img_id, $module_img_size[$i]); $i++; } wp_send_json($response); die(); }
1. add_action(“wp_ajax_module_img_fetch”, “module_img_fetch_func”) : This hook allows you to handle your custom AJAX endpoints. The wp_ajax_ hooks follows the format “module_img_fetch“, where “module_img_fetch” is the ‘action‘ field submitted to admin-ajax.php.This hook only fires for logged-in users.
2. add_action(“wp_ajax_nopriv_module_img_fetch”, “module_img_fetch_func”) : This hook only fires for non logged-in users. To allow both, you must register both hooks!
Register script to execute Ajax code
add_action('init', 'my_script_enqueuer'); function my_script_enqueuer() { wp_enqueue_script('jquery'); wp_enqueue_script('module_img_fetch_script', plugin_dir_url(__FILE__) . 'js/module_img_script.js', array('jquery')); wp_localize_script('module_img_fetch_script', 'moduleFetchAjax', array('ajaxurl' => admin_url('admin-ajax.php'), 'security' => wp_create_nonce('module_img_fetch_nonce'))); wp_enqueue_script('module_img_fetch_script'); }
1. add_action(‘init’, ‘my_script_enqueuer’) : “add_action” are the hooks that the WordPress core launches at specific points during execution, or when specific events occur. “init” Fires after WordPress has finished loading but before any headers are sent.
2. wp_enqueue_script : it refers to registering and adding scripts to your site.
Creating Widget functionality
Create folder “widgets” in folder “elementor-module”. next create file “image-module-widget.php” in folder “elementor-module/widgets” and add below code.
<?php class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { public function get_name() { return 'image_module_widget'; } public function get_title() { return esc_html__('Image Module', 'elementor-module'); } public function get_icon() { return 'eicon-image'; } public function get_categories() { return ['basic']; } public function get_keywords() { return ['image', 'module']; } protected function register_controls() { $this->start_controls_section( 'image_title', [ 'label' => esc_html__('Image', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ] ); $this->add_control( 'image', [ 'label' => esc_html__('Choose Image', 'elementor-module'), 'type' => \Elementor\Controls_Manager::MEDIA, 'default' => [ 'url' => \Elementor\Utils::get_placeholder_image_src(), ], ] ); $this->add_group_control( \Elementor\Group_Control_Image_Size::get_type(), [ 'name' => 'image', 'default' => 'large', ] ); $this->end_controls_section(); // Content Tab Start $this->start_controls_section( 'section_title', [ 'label' => esc_html__('Title', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ] ); $this->add_control( 'title', [ 'label' => esc_html__('Title', 'elementor-module'), 'type' => \Elementor\Controls_Manager::TEXTAREA, 'default' => esc_html__('Hello world', 'elementor-module'), ] ); $this->end_controls_section(); // Content Tab End $this->start_controls_section( 'content_section', [ 'label' => esc_html__('Content', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ] ); $this->add_group_control( \Elementor\Group_Control_Typography::get_type(), [ 'name' => 'content_typography', 'selector' => '{{WRAPPER}} .hello-world', ] ); $this->end_controls_section(); // Style Tab Start $this->start_controls_section( 'section_title_style', [ 'label' => esc_html__('Title Color', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_STYLE, ] ); $this->add_control( 'title_color', [ 'label' => esc_html__('Title Text Color', 'elementor-module'), 'type' => \Elementor\Controls_Manager::COLOR, 'selectors' => [ '{{WRAPPER}} .hello-world' => 'color: {{VALUE}};', ], ] ); $this->end_controls_section(); // Style Tab End } protected function render() { $settings = $this->get_settings_for_display(); ?> <input type="hidden" class="module_img_cls" value="<?php echo $settings['image']['id']; ?>" data-size="<?php echo $settings['image_size']; ?>" /> <div class="module_img_div_<?php echo $settings['image']['id']; ?>"><?php echo $img_path = '<img src = ' . plugin_dir_url( __DIR__ ) . 'img/loading-icon.gif >' ?></div> <p class="hello-world"> <?php echo $settings['title']; ?> </p> <?php } }
Widget Class
First, we need to create a class that extends the \Elementor\Widget_Base class:
class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { }
Widget Methods
A simple widget skeleton class will look as follows:
class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { public function get_name() {} public function get_title() {} public function get_icon() {} public function get_categories() {} public function get_keywords() {} public function get_custom_help_url() {} protected function get_upsale_data() {} public function get_script_depends() {} public function get_style_depends() {} protected function register_controls() {} protected function render() {} protected function content_template() {} }
Widget Data Methods
Widget data needs to be “returned” by certain methods. Those methods are simple:
<?php class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { public function get_name() { return 'image_module_widget'; } public function get_title() { return esc_html__('Image Module', 'elementor-module'); } public function get_icon() { return 'eicon-image'; } public function get_categories() { return ['basic']; } public function get_keywords() { return ['image', 'module']; } }
Name : The get_name() method returns the widget name as it will be used in the code.
Title : The get_title() method returns the widget label as it will be displayed to the user.
Icon : The get_icon() method is an optional, but recommended, method. It lets you set the widget icon. You can use any Elementor icons (opens new window)or FontAwesome icons (opens new window), to simply return the CSS class name.
Categories : The get_categories() method lets you set the category of the widget.
Keywords : The get_keywords() method lets you set widget keywords and is used to filter the widget list.
Registering Controls
In your widget class, you can add controls inside the register_controls() method as follows:
class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { protected function Elementor_Image_Module_Widget () { $this->start_controls_section(); $this->add_control(); $this->add_control(); $this->add_control(); $this->end_controls_section(); } }
Add Controls to Widget
below, we’re going to add a few controls to a widget to allow users save data:
class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { protected function register_controls() { $this->start_controls_section( 'image_title', [ 'label' => esc_html__('Image', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ] ); $this->add_control( 'image', [ 'label' => esc_html__('Choose Image', 'elementor-module'), 'type' => \Elementor\Controls_Manager::MEDIA, 'default' => [ 'url' => \Elementor\Utils::get_placeholder_image_src(), ], ] ); $this->add_group_control( \Elementor\Group_Control_Image_Size::get_type(), [ 'name' => 'image', 'default' => 'large', ] ); $this->end_controls_section(); // Content Tab Start $this->start_controls_section( 'section_title', [ 'label' => esc_html__('Title', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ] ); $this->add_control( 'title', [ 'label' => esc_html__('Title', 'elementor-module'), 'type' => \Elementor\Controls_Manager::TEXTAREA, 'default' => esc_html__('Hello world', 'elementor-module'), ] ); $this->end_controls_section(); // Content Tab End $this->start_controls_section( 'content_section', [ 'label' => esc_html__('Title Typography', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ] ); $this->add_group_control( \Elementor\Group_Control_Typography::get_type(), [ 'name' => 'content_typography', 'selector' => '{{WRAPPER}} .hello-world', ] ); $this->end_controls_section(); // Style Tab Start $this->start_controls_section( 'section_title_style', [ 'label' => esc_html__('Title', 'elementor-module'), 'tab' => \Elementor\Controls_Manager::TAB_STYLE, ] ); $this->add_control( 'title_color', [ 'label' => esc_html__('Text Color', 'elementor-module'), 'type' => \Elementor\Controls_Manager::COLOR, 'selectors' => [ '{{WRAPPER}} .hello-world' => 'color: {{VALUE}};', ], ] ); $this->end_controls_section(); // Style Tab End } }
start_controls_section() creates a new section.
end_controls_section() closes the section.
Every control has the following key parameters:
Section Name (string) – Unique id used in the code.
Section Setting (array) – Extra section parameters.
Label (string) – Label displayed to the user in the panel.
Tab (string) – Tab where the section is located. Default is content.
Conditions (array) – Control display conditions.
Elementor Tabs
Elementor uses tab navigation to display controls. When extending Elementor, you can use any tab you need, or create new ones.
Built-in Tabs
Elementor has 6 pre-defined tabs used in different panels:
Name/ID | Label | Constant |
---|---|---|
content | Content | \Elementor\Controls_Manager::TAB_CONTENT |
style | Style | \Elementor\Controls_Manager::TAB_STYLE |
advanced | Advanced | \Elementor\Controls_Manager::TAB_ADVANCED |
responsive | Responsive | \Elementor\Controls_Manager::TAB_RESPONSIVE |
layout | Layout | \Elementor\Controls_Manager::TAB_LAYOUT |
settings | Settings | \Elementor\Controls_Manager::TAB_SETTINGS |
In displays controls in a Content tab, allowing the user to set the widget content, and a Style tab to design the content. In addition, Elementor adds an Advanced tab to all widgets.
Media Control
Elementor Media control displays a media chooser section based on the WordPress media library.
When using this control, the type should be set to \Elementor\Controls_Manager::MEDIA constant.
Arguments
Name | Type | Default | Description |
---|---|---|---|
type | string | media | The type of the control. |
label | string | The label that appears above of the field. | |
description | string | The description that appears below the field. | |
show_label | bool | true | Whether to display the label. |
label_block | bool | true | Whether to display the label in a separate line. |
separator | string | default | Set the position of the control separator. Available values are default, before and after. default will hide the separator, unless the control type has specific separator settings. before / after will position the separator before/after the control. |
media_types | array | [‘image’] | Supported media types. Available values are image, video, svg, application/pdf etc. |
default | array | Default media values.
|
Image Size Group Control
Elementor image size group control show input fields to define one of the default image sizes like thumbnail, medium, medium_large, large or custom image dimensions
The control is describe in Group_Control_Image_Size class which extends Group_Control_Base class.
Arguments
Name | Type | Default | Description |
---|---|---|---|
type | string | image-size | The type of the control. |
separator | string | default | Set the position of the control separator. Available values are default, before and after. default will hide the separator, unless the control type has specific separator settings. before / after will position the separator before/after the control. |
include | array | Image sizes to include. | |
exclude | array | Image sizes to exclude. | |
default | string | The default image size. |
Textarea Control
Elementor textarea control displays a classic textarea field with an option to set the number of rows.
When using “Textarea Control” , the type should be set to \Elementor\Controls_Manager::TEXTAREA constant.
Arguments
Name | Type | Default | Description |
---|---|---|---|
type | string | textarea | The type of the control. |
label | string | The label that appears above of the field. | |
description | string | The description that appears below the field. | |
show_label | bool | true | Whether to display the label. |
label_block | bool | true | Whether to display the label in a separate line. |
separator | string | default | Set the position of the control separator. Available values are default, before and after. default will hide the separator, unless the control type has specific separator settings. before / after will position the separator before/after the control. |
rows | int | 5 | Number of rows. |
placeholder | string | The field placeholder that appears when the field has no values. | |
default | string | The field default value. |
Color Control
Elementor color control displays a color picker field with an alpha slider. It includes a customizable color palette that can be preset by the user.
When using this control, the type should be set to \Elementor\Controls_Manager::COLOR constant.
Arguments
Name | Type | Default | Description |
---|---|---|---|
type | string | color | The type of the control. |
label | string | The label that appears above of the field. | |
description | string | The description that appears below the field. | |
show_label | bool | true | Whether to display the label. |
label_block | bool | false | Whether to display the label in a separate line. |
separator | string | default | Set the position of the control separator. Available values are default, before and after. default will hide the separator, unless the control type has specific separator settings. before / after will position the separator before/after the control. |
alpha | bool | true | Whether to allow alpha channel. |
default | string | Default color in RGB, RGBA, or HEX format. |
Typography Group Control
Elementor typography group control displays input fields to define the content typography including font size, font family, font weight, text transform, font style, line height and letter spacing.
When using this group control, the type should be set to Group_Control_Typography::get_type() method.
Arguments
Name | Type | Default | Description |
---|---|---|---|
type | string | typography | The type of the control. |
separator | string | default | Set the position of the control separator. Available values are default, before and after. default will hide the separator, unless the control type has specific separator settings. before / after will position the separator before/after the control. |
exclude | array | Exclude some controls from the group control. Example: [‘font_style’] |
Widget Rendering
The last step in Elementor Widget development is to display the output. Each widget needs to render the data returned from the controls, and generate the final HTML displayed in the frontend and the preview area.
class Elementor_Image_Module_Widget extends \Elementor\Widget_Base { protected function render() { $settings = $this->get_settings_for_display(); ?> <input type="hidden" class="module_img_cls" value="<?php echo $settings['image']['id']; ?>" data-size="<?php echo $settings['image_size']; ?>" /> <div class="module_img_div_<?php echo $settings['image']['id']; ?>"><?php echo $img_path = '<img src = ' . plugin_dir_url( __DIR__ ) . 'img/loading-icon.gif >' ?></div> <p class="hello-world"> <?php echo $settings['title']; ?> </p> <?php } }
Rendering Methods
Elementor has rendering method, depend on the returned values from the control.
render() – It is written as a PHP template that generates output in the frontend.
Download Full Code Plugin
Suggested post : How to Create WordPress Widget