Hello!
Yes of course WPBakery / Visual Composer is bloated. Absolutely correct its more ideal to simply create your own page template with a custom WordPress query and design your own post grid from scratch.
For smaller budget WordPress projects where time is money, it is sometimes ideal to go the post grid route. Why not? The customer wants the designed and customized end result but they have a restricted budget.
WPBakery (aka “Visual Composer”) does save time in these scenarios, and there’s something to be said about applying customized CSS and jQuery to customize and tailor the vanilla packaged look and feel that these types of WordPress bundled solutions usually bring to the table.
All that said, the point of this post is to describe how to properly inject custom ACF fields (advanced custom fields fields) into your post grids. Why would you want to do that? Well if you have things like an author avatar, author bio or any number of custom blog or custom post type fields that you want injected into your grid, this could definitely be useful.
Why is this a tricky endeavor in the first place?
WPBakery post grid, and possibly many other post grid solutions for that matter, make heavy use of jQuery admin-ajax.php queries to poll and populate the post grids in a dynamic way. This means that the data is being polled internally by the plugin via an Ajax query in custom generated jQuery by the plugin. If you just create a custom shortcode that uses the built-in ACF get_field function, it wont work. This is because you wont know your post ID during the time the content is being polled via Ajax on the PHP level.
Furthermore, because of the asynchronous nature of these jQuery based Ajax calls, the order of the post grid when the data is rendered is not as predictable as a custom PHP based page template with a bootstrap grid would be, alternatively.
This means that we have to go further than just a custom shortcode that each grid item will render. We need to have the custom shortcode render the data using jQuery in a similar way.
For us, this is more of a challenge to work around these types of limitations you see in these bloated bundled plugin solutions.
Create your custom fields and assign to the post
I wont describe how to do that here other than a quick overview. In ACF , create your custom fields and set the conditional rules within the field group to show up if the post type is “post”. You can also position them to show up at different sections of the add/edit post screen.
For the purpose of this post, we’ll call our custom field “Blog Author” , or “blog_author”. This field will be a select dropdown with several author names. The idea is that the person making the post isn’t the author (i.e. in a corporate environment where a marketing person is posting an article penned by someone else).
Lets assume the field is created and populated for all the posts that will show up in the grid.
Create custom shortcode to render the ACF in your WPBakery post grid
In your functions.php file, you want to create a custom shortcode that specifically is designed to be used by WPBakery Visual Composer Post grid. The shortcode basically adds data from the custom field and create a variable that can be used in jQuery when rendering the output.
add_filter( 'vc_grid_item_shortcodes', 'shift8_module_add_grid_shortcodes' ); function shift8_module_add_grid_shortcodes( $shortcodes ) { $shortcodes['shift8_blog_author'] = array( 'name' => __( 'blog_author', 'my-text-domain' ), 'base' => 'vc_post_id', 'category' => __( 'Content', 'my-text-domain' ), 'description' => __( 'Show current post author', 'my-text-domain' ), 'post_type' => Vc_Grid_Item_Editor::postType(), ); return $shortcodes; }
All that is happening above is we are creating a shortcode called [ shift8_blog_author ], with the custom field we created earlier called blog_author. The short code will be used in the custom grid editor template, wherever you like.
Render the ACF field in your WPBakery Visual Composer post grid
This is the most interesting part! Now that we are triggering the shortcode in our post grid, we want to render data in a way that is compatible with how the post grid is rendered in the first place. With a PHP post grid page template, things are rendered in a regimented, controlled and linear way (so to speak). With the jQuery admin-ajax polling that happens to render content, its less predictable in terms of how we can manipulate content or inject custom content (as in this scenario).
What we want to do is render content placeholders with unique container IDs, then render jQuery that injects content in the proper placeholders regardless of the order. This means that even if the content rendered in a weird order, jQuery will find the correct container IDs and inject the correct corresponding content.
add_shortcode( 'shift8_blog_author', 'shift8_blog_author_render' ); function shift8_blog_author_render() { $shortcode_output = ' {{ post_data:ID }} {{ post_data:ID }}'; return $shortcode_output; }
The main thing to note in the above snippet is the {{ post_data:blog_author }}. These are WPbakery’s way of pulling content from the feed during the admin-ajax calls that it is making in order to render the grid. This variable will pull the ACF field and assign it to author_name to be used later.
The placeholder container that we will ultimately be injecting content into with jQuery is the following :
Note the ID will have the custom post ID for that particular grid item, rendered with the handy WPBakery injected field. Then when we actually have the data to inject, because again this is all happening at different times due to the nature of ajax and jQuery/javascript, we inject the content :
jQuery("#shift8-blogauthor-name-{{ post_data:ID }}").append(author_name);
You can do this in a few different ways with jQuery, especially from a design perspective. Hopefully once you grasp the methodology you will see that there is room for further customization here.
There are always many different use cases, needs and requirements for web projects. Having everything custom developed, ground up and custom is not always possible with the lower budget projects. Hopefully you found this useful!