0

I have the following code (view.js) for a Gutenberg block which uses the Interactivity API that renders posts when clicking a button:

import { store, getContext, getElement } from '@wordpress/interactivity';

store('my-store', {
    callbacks: {
        renderContent() {
            const context = getContext();
            const element = getElement();
            if (context.posts !== null) {
                var html = '';
                for (var i = 0; i < context.posts.length; i++) {
                    var post = context.posts[i];
                    html += '<article id="post-' + post.id + '" class="wp-block-infinite-latest-posts__post">';
                    html += '<h2 class="wp-block-infinite-latest-posts__post-title">' + post.title.rendered + '</h2>';
                    html += '<div class="wp-block-infinite-latest-posts__post-content">' + post.content.rendered + '</div>';
                    html += '</article>';
                }
                context.offset = context.offset + context.number;
                element.ref.innerHTML += html;
            }
        },
    },
    actions: {
        *getPosts() {
            const context = getContext()
            const posts = yield fetch(
                'https://' + window.location.hostname + '/wp-json/wp/v2/posts?per_page=' + encodeURIComponent(context.number) + '&offset=' + encodeURIComponent(context.offset) + '&categories=' + encodeURIComponent(context.category)
            ).then(function (response) {
                return response.json()
            })
            context.posts = posts;
        },
    }
});

This is the render code in PHP:

<?php
    $block_attributes = get_block_wrapper_attributes()
?>
<div
    <?php echo $block_attributes; ?>
    data-wp-interactive="my-store"
    <?php
    echo wp_interactivity_data_wp_context(
        array(
            'posts'    => null,
            'number'   => $attributes['number'],
            'offset'   => 0,
            'category' => $attributes['category'],
        )
    );
    ?>
>
    <div data-wp-watch="callbacks.renderContent"></div>
    <button data-wp-on--click="actions.getPosts">Load more</button>
</div>

The code works, but the user must click the 'Load more' button to display the first n posts. How can I modify my code so that the first n posts are rendered when the page loads? Is there an Interactivity API directive for this?

1 Answer 1

1

You could consider running actions.getPosts on mount via data-wp-init like:

<div … data-wp-init="actions.getPosts">

As per the documentation:

This directive runs a callback only when the node is created.

You could also consider server-rendering the initial set of posts, like:

<div data-wp-watch="callbacks.renderContent">
  <?php
  $query = new WP_Query(
    array(
      …
    )
  );
  ?>
  <?php while( $query->have_posts() ) : ?>
    …

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.