Manual and custom pagination in Laravel (without Eloquent)

- Andrés Cruz

En español
Manual and custom pagination in Laravel (without Eloquent)

Many times we need to have some organization or grouping on some set of elements, whether it comes from the database or not, and by organization I mean being able to display a set of these elements or data on demand and that we can organize them in a group and go visiting each of these groups at will; basically this is pagination and we are going to see how we can manually paginate in Laravel without the need to use Eloquent or connections to the database.

In any project in Laravel, we have different mechanisms to do the pagination according to the official documentation, both automatic and to paginate a set of data or lists easily.

Let's start by defining what pagination is.

What is pagination?

Pagination in Laravel is a functionality integrated into this type of framework as Laravel is; using paging, you can split a large data set into chunks; that is, if we have 30 records and we want to paginate by 10, we have 3 groups or pages; to move between pages, an index is used.

Although it seems little, pagination is an ideal method to simplify the records to be displayed; let's suppose that we don't have 30 records, but about 500 or more, and you want to show a paged list of 10 levels again, using pagination we can divide all the records pull and show 10 by 10; to go to another group, we simply click on a link and go to the next group; this avoids having an extremely heavy page, with 500 or more records, avoids generating such a large page and what it entails loading it.

This is accomplished using Eloquent's paginate() or simplePaginate() methods, which take care of cutting the query results into multiple pages based on the number of records we want to display on each one.

Pagination is a number of pages that corresponds to the number of pointed links that generally appears at the bottom of a web page that serves to separate content and separate content into parts.

To use pagination, we use something like:

Post::pagination(10)

To have a 10 level pagination, additionally, you can put more Eloquent methods like where to customize the query.

Another example of pagination in Laravel

Supongamos que tenemos una tabla de "Posts" en nuestra base de datos que queremos mostrar en una vista. Queremos mostrar solo 10 resultados por página.

En el controlador:

public function index()
{
    $posts = DB::table('posts')->paginate(10);
    return view('posts.index', ['posts' => $posts]);
}

In the view:

@foreach ($posts as $post)
    <p>{{ $post->title }}</p>
@endforeach

{{ $posts->links() }}

The paginate() method divides the query into pages of 10 elements each, and the links() method generates the links to navigate between the different pages. Thus, in the view, the first 10 results and a set of links to access the following pages will be displayed.

This is just a basic example, Laravel offers us several options to customize the appearance and behavior of the pagination to adapt it to our needs, some of which we will see in the following sections.

Manual pagination in Laravel

For this, we have a couple of very similar classes in Laravel that we can use with a very similar operation, the simplest would be called Paginator and it has the following structure:

__construct($items, $perPage, $currentPage = NULL, array $options = [])

As you can guess, the first two arguments are mandatory, which correspond to the data set and the pagination level (although we are the ones who have to indicate the data to show how we will see a little later).

We are going to work with the following data model:

$elements = range(1, 123);

In which, we simply have an array of 123 elements ranging from 1 to 123.

The simplest pagination we can build looks like this:

$res = new Paginator($currentElements, 10);

In which we only specify the data and how many elements we are going to page; which in this case would be 10; we are going to make a dd of the variable $res:

Paginación simple

Here, as you can see, we have everything we need, the control variables to know data about the pagination and the items.

Paginate with Paginator

If we do a dd of this we saw that we have the previous structure, just with the items to page, now what happens if we want to go to another page; for that we have to indicate a third parameter, if we place the following parameter, we will see that:

$res = new Paginator($currentElements, 10, 3); 
Paginar problema en el currentPage

Basically nothing changes, it continues to give the same result regardless of the pagination level we indicate, which in this case we are indicating that we want to go to page number 3.

If we want to paginate, we have to do it manually; for example:

$currentPage = 3;
$perPage = 10;
 
$currentElements = array_slice($elements, $perPage * ($currentPage - 1), $perPage);
 
$res = new Paginator($currentElements, $perPage, $currentPage);

And if we do a dd:

Paginado correctamente

Now we do have our paginated data.

Dynamic pagination based on passing parameters

As we see a little later, we can pass some parameters to obtain the index of which page our user wants to see, for the moment abstract from this and suppose that we are going to receive this information from our view in a parameter that by default is called page; therefore, since they are data that we are going to receive from our user and that with this we are only going to consult data, therefore, we are going to receive it via get.

So in summary:

$currentPage = $request->page;
$perPage = 10;
 
$currentElements = array_slice($elements, $perPage * ($currentPage - 1), $perPage);
 
$res = new Paginator($currentElements, $perPage, $currentPage);

With this, we can receive which page our user wants to see and build the list to display on demand.

Visualize results in a view

Remember that we also have a function called link that is responsible for painting the pagination links in the view; by default, it uses the Bootstrap layout if you configured your project that way:

@foreach ($res as $r)
    {{ $r }}
@endforeach
 
{{ $res->links() }} 
Enlaces de paginación

Paginate with LengthAwarePaginator

Now, we have another class that we can use which would be the LengthAwarePaginator whose only difference would be that it receives all the elements with which we are going to work:

__construct($items, $total, $perPage, $currentPage = NULL, array $options = [])

So, let's take our example to:

$currentPage = $request->page;
$perPage = 10;
 
$currentElements = array_slice($elements, $perPage * ($currentPage - 1), $perPage);
 
$res = new LengthAwarePaginator($currentElements, count($elements), $perPage, $currentPage);

Otherwise everything is exactly the same; let's make a dd of the above:

Length Paginator

Options for pagination

For both variants, we have one more parameter that would be to do the pagination:

$res = new LengthAwarePaginator($currentElements, count($elements), $perPage, $currentPage, ['path' => url('dashboard/category')]);

Or simply:

$res->setPath('/dashboard/category');

This would be used by the links function in our view to place as part of the path in the navigation links:

Length Paginator Path

Remember that this is one of the many topics that we work on in our Laravel course that you can take from the courses section.

Andrés Cruz

Develop with Laravel, Django, Flask, CodeIgniter, HTML5, CSS3, MySQL, JavaScript, Vue, Android, iOS, Flutter

Andrés Cruz In Udemy

I agree to receive announcements of interest about this Blog.