5

I am working with Elementor in Wordpress. I display my Custom Post Type with the posts widget. I have created an AJAX filter which additionally filters my posts by different values - which works so far.

Now I am facing the problem that I am not able to rerender the elementor post widget. This is mandatory to get the filtered results within the widget because elementor only allows server-site filtering by default.

I am using Custom Query Filter (https://developers.elementor.com/custom-query-filter/) to push the filter results into the elementor post widget.

Basically my question is if there is an elementor function which I can call with ajax to rerender elementor widgets.

stheobald
  • 51
  • 3
  • 1
    Hi, maybe `ajax_render_widget`: https://code.elementor.com/methods/elementor-widgets_manager-ajax_render_widget/ can be of help for that, but haven't really used it so I can't provide a proper answer. – Andreas Myriounis Nov 16 '20 at 16:54

1 Answers1

2

Took me a while to figure this out, but I have a method that works:

  1. You need to pass through the current post ID and the widget's ID to your AJAX method:

Widget's ID: Can be found on the wrapper div of your widget in the data-id attribute.

Post ID: Elementor actually already stores this in a javascript global: window.elementorFrontendConfig.post.id

  1. Inside your AJAX action, use the following function to render a widget from the specified Post ID and Widget ID:
function render_element($postid, $elementid)
{
    $document = \Elementor\Plugin::$instance->documents->get( $postid );

    if ( ! $document ) {
        return new \WP_Error(
            'document_not_exist',
            __( 'Document doesn\'t exist', 'elementor-pro' ),
            [ 'status' => 404 ]
        );
    }

    $element_data = $document->get_elements_data();
    $widget = \Elementor\Utils::find_element_recursive( $element_data, $elementid );

    if ( empty( $widget ) ) {
        return new \WP_Error(
            'Element_not_exist',
            __( 'Posts widget doesn\'t exist', 'elementor-pro' ),
            [ 'status' => 404 ]
        );
    }

    // Override the global $post for the render.
    query_posts(
        [
            'p' => $postid,
            'post_type' => 'any',
        ]
    );

    \Elementor\Plugin::$instance->documents->switch_to_document( $document );
    $html = $document->render_element($widget);

    //Not sure if this is needed in AJAX context:
    // \Elementor\Plugin::$instance->documents->restore_document();
    // \wp_reset_query();

    return [
        'content' => $html,
    ];
}
Mikepote
  • 6,042
  • 3
  • 34
  • 38