CodeIgniter4 分頁(yè)類

2020-08-17 16:59 更新

CodeIgniter 提供了一個(gè)非常簡(jiǎn)單但靈活的分頁(yè)庫(kù),該庫(kù)主題簡(jiǎn)單,可以在 Model 中使用,并能夠在單個(gè)頁(yè)面上支持多個(gè)分頁(yè)器。

加載庫(kù)

與 CodeIgniter 中的所有服務(wù)一樣,它可以通過(guò) Config\Services 進(jìn)行加載,盡管通常它并不需要手動(dòng)加載:

$pager = \Config\Services::pager();

分頁(yè)數(shù)據(jù)庫(kù)結(jié)果

通常,可以使用分頁(yè)器庫(kù)對(duì)從數(shù)據(jù)庫(kù)中檢索到的結(jié)果進(jìn)行分頁(yè)。使用 Model 類時(shí),可以使用其內(nèi)置的 paginate() 方法來(lái)自動(dòng)檢索當(dāng)前批次的結(jié)果,并設(shè)置 Pager 庫(kù),以便可以在控制器中使用它。它甚至可以通過(guò) page=X 變量從當(dāng)前 URL 讀取當(dāng)前應(yīng)顯示的頁(yè)面。

在你的應(yīng)用程序中提供用戶的分頁(yè)列表時(shí),控制器的方法應(yīng)類似于:

<?php namespace App\Controllers;


use CodeIgniter\Controller;


class UserController extends Controller
{
    public function index()
    {
        $model = new \App\Models\UserModel();


        $data = [
            'users' => $model->paginate(10),
            'pager' => $model->pager
        ];


        echo view('users/index', $data);
    }
}

在上面的示例中,我們首先創(chuàng)建了 UserModel 的實(shí)例。然后,我們對(duì)它填充數(shù)據(jù)來(lái)發(fā)送到視圖。第一個(gè)元素是來(lái)自數(shù)據(jù)庫(kù) users 的結(jié)果, 這將針對(duì)正確的頁(yè)面進(jìn)行檢索,每頁(yè)會(huì)返回 10 個(gè)用戶。發(fā)送到視圖的第二個(gè)必須的項(xiàng)是 Pager 實(shí)例本身。為了方便起見,Model 將會(huì)保留所使用的實(shí)例, 并將其存儲(chǔ)在 public 類變量 $pager 中。因此,我們將其獲取并將其分配給視圖中的 $pager 變量。

然后,在視圖內(nèi),我們需要告訴它應(yīng)該在哪里顯示結(jié)果的鏈接:

<?= $pager->links() ?>

就是這樣。Pager 類將為當(dāng)前頁(yè)面兩側(cè)超過(guò)兩個(gè)頁(yè)面的任何頁(yè)面呈現(xiàn)“首頁(yè)”和“末頁(yè)”的鏈接,以及“下一頁(yè)”和“上一頁(yè)”的鏈接。

如果你更喜歡簡(jiǎn)單的輸出,則可以使用 simpleLinks() 方法,它會(huì)輸出“較舊”和“較新”鏈接而不是有著詳細(xì)信息的分頁(yè)鏈接:

<?= $pager->simpleLinks() ?>

在后臺(tái)中,庫(kù)加載了一個(gè)視圖文件,文件確定鏈接的格式,從而可以輕松地根據(jù)需要進(jìn)行修改。有關(guān)如何完全自定義輸出的詳細(xì)信息,請(qǐng)參見下文。

分頁(yè)多個(gè)結(jié)果

如果需要提供來(lái)自兩個(gè)不同的結(jié)果集的鏈接,則可以將組名傳遞給大多數(shù)分頁(yè)方法,以使數(shù)據(jù)分開:

// 在控制器文件中:
public function index()
{
    $userModel = new \App\Models\UserModel();
    $pageModel = new \App\Models\PageModel();


    $data = [
        'users' => $userModel->paginate(10, 'group1'),
        'pages' => $pageModel->paginate(15, 'group2'),
        'pager' => $userModel->pager
    ];


    echo view('users/index', $data);
}


// 在視圖文件中:
<?= $pager->links('group1') ?>
<?= $pager->simpleLinks('group2') ?>

手動(dòng)分頁(yè)

你可能會(huì)發(fā)現(xiàn)有時(shí)候只需要根據(jù)已知數(shù)據(jù)來(lái)創(chuàng)建分頁(yè)。這時(shí)你可以使用 makeLinks() 方法來(lái)手動(dòng)創(chuàng)建鏈接,這個(gè)方法分別將當(dāng)前頁(yè)面, 每頁(yè)的結(jié)果數(shù)和項(xiàng)目總數(shù)作為第一個(gè),第二個(gè)和第三個(gè)參數(shù):

<?= $pager->makeLinks($page, $perPage, $total) ?>

默認(rèn)情況下,這將以正常方式將鏈接顯示為一組鏈接,你還可以通過(guò)將模板名稱作為第四個(gè)參數(shù)傳入來(lái)更改使用的顯示模板。在以下各節(jié)中可以找到更多詳細(xì)信息。

<?= $pager->makeLinks($page, $perPage, $total, 'template_name') ?>

也可以使用 URI 字段(segment)而不是用查詢參數(shù)來(lái)表示頁(yè)碼,只需指定字段號(hào)即可用作的第五個(gè)參數(shù) makeLinks() 。然后,由分頁(yè)器生成的 URI 看起來(lái)會(huì)像 https://domain.tld/model/『頁(yè)碼 而不是 https://domain.tld/model?page=『頁(yè)碼 。

<?= $pager->makeLinks($page, $perPage, $total, 'template_name', $segment) ?>

請(qǐng)注意: $segment 的值不能大于 URI 字段的數(shù)量加 1。

如果你需要在一頁(yè)上顯示很多分頁(yè)器,那么定義組的其他參數(shù)可能會(huì)有所幫助:

$pager = service('pager');
$pager->setPath('path/for/my-group', 'my-group'); // 另外,你可以為每個(gè)組定義路徑
$pager->makeLinks($page, $perPage, $total, 'template_name', $segment, 'my-group');

僅使用預(yù)期查詢進(jìn)行分頁(yè)

默認(rèn)情況下,所有 GET 查詢都顯示在分頁(yè)鏈接中。

例如,當(dāng)訪問(wèn) URL http://domain.tld?search=foo&order=asc&hello=i+am+here&page=2 時(shí),可以生成 頁(yè)面 3 鏈接以及其他鏈接,如下所示:

echo $pager->links();
// 頁(yè)面 3 鏈接: http://domain.tld?search=foo&order=asc&hello=i+am+here&page=3

only() 方法還允許你將其限制為僅已預(yù)期的查詢:

echo $pager->only(['search', 'order'])->links();
// 頁(yè)面 3 鏈接: http://domain.tld?search=foo&order=asc&page=3

page 查詢默認(rèn)情況下啟用。并 only() 在所有分頁(yè)鏈接中起作用。

自定義鏈接

查看配置

當(dāng)鏈接呈現(xiàn)到頁(yè)面時(shí),它們使用視圖文件來(lái)渲染 HTML。你可以通過(guò)編輯 app/Config/Pager.php 來(lái)輕松地更改使用的視圖:

public $templates = [
    'default_full'   => 'CodeIgniter\Pager\Views\default_full',
    'default_simple' => 'CodeIgniter\Pager\Views\default_simple'
];

設(shè)置存儲(chǔ)應(yīng)使用的視圖的別名和 命名空間的視圖路徑 。 default_fulldefault_simple 視圖會(huì)分別被用于 links()simpleLinks() 方法。要更改在整個(gè)應(yīng)用程序范圍內(nèi)顯示的方式,你可以在處分配一個(gè)新視圖。

例如,假設(shè)你創(chuàng)建一個(gè)與 Foundation CSS 框架一起使用的新視圖文件,然后將文件放在 app/Views/Pagers/foundation_full.php 中。 由于 application 目錄的命名空間為 App ,并且其下的所有目錄都直接映射到命名空間的各個(gè)部分,因此你可以通過(guò)其命名空間找到視圖文件:

'default_full'   => 'App\Views\Pagers\foundation_full',

但是,由于它位于標(biāo)準(zhǔn)的 app/Views 目錄下,因此不需要命名空間,因?yàn)?code>view() 方法可以按文件名定位它。在這種情況下,你只需提供子目錄和文件名:

'default_full'   => 'Pagers/foundation_full',

創(chuàng)建視圖并將其配置好后,將會(huì)自動(dòng)使用它。你不必替換現(xiàn)有模板。你也可以在配置文件中根據(jù)需要?jiǎng)?chuàng)建的任意數(shù)量的其他模板。常見的情況是你的應(yīng)用程序的前端和后端需要不同的樣式。

public $templates = [
    'default_full'   => 'CodeIgniter\Pager\Views\default_full',
    'default_simple' => 'CodeIgniter\Pager\Views\default_simple',
    'front_full'     => 'App\Views\Pagers\foundation_full',
];

配置完成后,你可以指定它作為 links() 、 simpleLinks() 以及 makeLinks() 方法的最后的一個(gè)參數(shù):

<?= $pager->links('group1', 'front_full') ?>
<?= $pager->simpleLinks('group2', 'front_full') ?>
<?= $pager->makeLinks($page, $perPage, $total, 'front_full') ?>

創(chuàng)建視圖

創(chuàng)建新視圖時(shí),只需要?jiǎng)?chuàng)建生成分頁(yè)鏈接本身所需的代碼。你不應(yīng)該創(chuàng)建不必要的包裝 div,因?yàn)樗赡軙?huì)在多個(gè)地方使用,并且這會(huì)限制它們的用途。這里通過(guò)向你展示現(xiàn)有的 default_full 模板,來(lái)演示創(chuàng)建新視圖:

<?php $pager->setSurroundCount(2) ?>


<nav aria-label="Page navigation">
    <ul class="pagination">
    <?php if ($pager->hasPrevious()) : ?>
        <li>
            <a href="<?= $pager->getFirst() ?>" aria-label="First">
                <span aria-hidden="true">First</span>
            </a>
        </li>
        <li>
            <a href="<?= $pager->getPrevious() ?>" aria-label="Previous">
                <span aria-hidden="true">«</span>
            </a>
        </li>
    <?php endif ?>


    <?php foreach ($pager->links() as $link) : ?>
        <li <?= $link['active'] ? 'class="active"' : '' ?>>
            <a href="<?= $link['uri'] ?>">
                <?= $link['title'] ?>
            </a>
        </li>
    <?php endforeach ?>


    <?php if ($pager->hasNext()) : ?>
        <li>
            <a href="<?= $pager->getNext() ?>" aria-label="Previous">
                <span aria-hidden="true">»</span>
            </a>
        </li>
        <li>
            <a href="<?= $pager->getLast() ?>" aria-label="Last">
                <span aria-hidden="true">Last</span>
            </a>
        </li>
    <?php endif ?>
    </ul>
</nav>

setSurroundCount()

在第一行中,setSurroundCount() 方法指定了我們要顯示到當(dāng)前頁(yè)面鏈接兩側(cè)的兩個(gè)鏈接。它接受的唯一參數(shù)是要顯示的鏈接數(shù)。

hasPrevious() & hasNext()

如果根據(jù)傳遞給 setSurroundCount 的值,如果當(dāng)前頁(yè)面的任何一側(cè)上可以顯示更多鏈接,則這些方法將返回布爾值 true。例如,假設(shè)我們有 20 頁(yè)數(shù)據(jù),當(dāng)前頁(yè)面是第 3 頁(yè),如果周圍的計(jì)數(shù)是 2,則以下鏈接將顯示在列表中:1、2、3、4 和 5。由于要顯示的第一個(gè)鏈接是第 1 頁(yè),但是頁(yè)面 0 并不存在,因此 hasPrevious() 會(huì)返回 false 。但是, hasNext() 將返回 true ,因?yàn)樵诘?5 頁(yè)之后還有 15 個(gè)額外的結(jié)果頁(yè)。

getPrevious() & getNext()

這兩個(gè)方法返回編號(hào)鏈接兩側(cè)上一頁(yè)或下一頁(yè)結(jié)果的 URL。有關(guān)完整說(shuō)明,請(qǐng)參見上一段。

getFirst() & getLast()

getPrevious()getNext() 類似,這兩個(gè)方法返回指向結(jié)果集中第一頁(yè)和最后一頁(yè)的鏈接。

links()

返回所有有關(guān)編號(hào)鏈接的數(shù)據(jù)數(shù)組。每個(gè)鏈接的數(shù)組都包含鏈接的 uri,標(biāo)題(只是數(shù)字)和一個(gè)布爾值,布爾值表示鏈接為當(dāng)前鏈接還是活動(dòng)鏈接:

$link = [
        'active' => false,
        'uri'    => 'http://example.com/foo?page=2',
        'title'  => 1
];
以上內(nèi)容是否對(duì)您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號(hào)
微信公眾號(hào)

編程獅公眾號(hào)