Jump to content

Paginating Comments using PW built-in Pagination in Uikit 3 Site/Blog Profile


Edison
 Share

Recommended Posts

When a blog post article receives many comments ? your start to consider to apply pagination to comments. Looking around this forum, I found some useful hints, but I couldn't find how to take full advantage of PW built-in pagination. In particular the ukBlogPosts() function in Uikit 3 Site/Blog Profile renders a list of paginated posts. ukBlogPosts() is calling a ukPagination() function which permits to navigate the posts. ? After some unsuccessful attempts to use it with CommentArray … ? I decided to insist. ? And here is the result.

The ukPagination() function in _uikit.php expects an argument $items of type PageArray. Of course a CommentArray ... is not a PageArray ... ? so we have to remove this blocking point. Going deeper inside the function you will notice that pagination is achieved through a call to a render() method of MarkupPagerNav. Let's look at its declaration:

public function ___render(WirePaginatable $items, $options = array())

Interesting ? here $items are declared of type WirePaginatable. What's that? ? a class? No! It's an interface! ? Looking around further I discovered that WirePaginatable interface is used by PageArray, PaginatedArray, and CommentArray.. bingo! ?? We got what to do first, modify ukPagination() function in _uikit.php changing $items argument type from PageArray to WirePaginatable:

//function ukPagination(PageArray $items, $options = array()) {
function ukPagination(WirePaginatable $items, $options = array()) { //>>>>> REPLACE WITH THIS LINE

Now the function accepts our CommentArray as argument, but to make it work we need to set its Limit, Start, and Total attributes as PW does automatically when dealing with pages. In order to do that we will use the WirePaginatable methods setLimit(), setStart(), setTotal(). In this process our Start attribute will have to be calculated dynamically to consider the page number when navigating the comments. To do that we will largely ? modify the function ukComments() in _uikit.php:

 function ukComments(CommentArray $comments, $options = array()) {

 	if(!$comments->count) { //>>>>>NEW-start
 		if(input()->pageNum > 1) {
 			// redirect to first pagination if accessed at an out-of-bounds pagination
 			session()->redirect(page()->url);
 		}
 		return '';
 	} //>>>>>NEW-end

 	$defaults = array(
 		'id' => 'comments',
 		'paginate' => false, //>>>>>NEW
 		'limit' => 3, //>>>>>NEW
 	);

 	//if(!count($comments)) return '';
 	$options = _ukMergeOptions($defaults, $options);

 	$language = user()->language->id; //>>>>>NEW
 	$comments = $comments->find("language=$language"); //>>>>>NEW

 	if($options['paginate']) { //>>>>>NEW-start
 		$limit = $options['limit'];
 		$start = (wire()->input->pageNum - 1) * $limit;
 		$total = $comments->count();
 		$comments = $comments->slice($start, $limit);
 		$comments->setLimit($limit);
 		$comments->setStart($start);
 		$comments->setTotal($total);
 	} //>>>>>NEW-end

 	$out = "<ul id='$options[id]' class='uk-comment-list'>";

 	foreach($comments as $comment) {
 		$out .= "<li class='uk-margin'>" . ukComment($comment) . "</li>";
 	}

 	$out .= "</ul>";

 	if($options['paginate'] && $comments->getTotal() > $comments->count()) { //>>>>>NEW-start
 		$out .= ukPagination($comments);
 	} //>>>>>NEW-end

 	return $out;
 }

As you will notice we have added two options to the function [paginate => false] and [limit => 3]. In such a way the ukComments() function will operate as before. If you wish to use pagination you will have to pass [paginate => true] as argument of the function. Of course you can freely choose the limit value or by pre-setting it in the function or by passing it as an argument to the function.

Please note that the modification implements the necessary changes (2 lines) to make comments language-aware as described in the tutorial:

We are now just to steps away to see our paginated comments. ?

First you will need to enable pagination in the templates where you want comments to be paginated. Login to PW Admin and select your template. In the tab URLs enable the "Allow Page Numbers?" option.

817476474_ScreenShot2019-07-11at11_42_49.thumb.png.a6ae0420544579ea695fd1f1a5ccb3d0.png

Second you will need to modify the associated php template, in our example blog-post.php, to change the call to ukComments() as follows (sorting is not necessary, depends on your preferences):

//echo ukComments($comments);
echo ukComments($comments->find("sort=-created"), ['paginate' => true]); //>>>>> REPLACE WITH THIS LINE

And here we are! Below a snapshot our paginated comments! ???

1777250541_ScreenShot2019-07-11at11_53_49.thumb.png.026a01fd03677f87f8d99f8d6ce08215.png

As you can see on the bottom of the comments you have the standard PW pagination navigator, without being forced to rewrite a new one for the purpose! ?

I hope you can find something useful with this tutorial.

  • Like 7
  • Thanks 2
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...