首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 相關知識

Yii2 GridView 進階實戰:核心功能、kartik-v/yii2-grid 擴展深度配置與導出、合併欄位、固定表頭技巧

     編輯:PHP 相關知識

Yii2 內建 GridView 核心功能速覽

GridView 是 Yii2 最強大的資料表格小部件,支援排序、分頁、篩選、欄位客製化、關聯資料顯示。

1. 四大內建欄位類型

類別用途關鍵屬性
DataColumn一般資料欄(預設)attribute, label, value, format, filter
ActionColumn操作按鈕(檢視/編輯/刪除)template, buttons, controller
CheckboxColumn列選框(批次操作)name, checkboxOptions
SerialColumn自動序號header

2. 欄位客製化常用屬性

[
    'label' => '自訂標題',           // 覆蓋 attributeLabels()
    'attribute' => 'id',             // 對應模型屬性,支援排序
    'value' => function ($model) {   // 客製化顯示內容(閉包)
        return $model->name . ' (' . $model->email . ')';
    },
    'format' => 'raw',               // raw/html/ntext/date/email/url/image/boolean
    'visible' => true,               // 是否顯示
    'headerOptions' => ['width' => '120'], // 表頭樣式
    'contentOptions' => ['class' => 'text-center'],
]

3. 資料提供者與排序分頁配置

// 控制器中
$dataProvider = new ActiveDataProvider([
    'query' => $query,
    'pagination' => ['pageSize' => 15],  // 預設 20
    'sort' => ['attributes' => ['id', 'created_at']], // 僅允許這些欄位排序
]);

若使用 SearchModel,在 search() 方法中設定。

4. 下拉式篩選(如狀態)

// Model 定義狀態常數與標籤映射
const STATUS_DELETED = 0;
const STATUS_ACTIVE = 10;
public static function getStatusLabels($key = null) {
    $labels = ['' => '請選擇', self::STATUS_DELETED => '停用', self::STATUS_ACTIVE => '啟用'];
    return $key === null ? $labels : ($labels[$key] ?? '未知');
}

// GridView 欄位配置
[
    'attribute' => 'status',
    'filter' => Html::activeDropDownList($searchModel, 'status', User::getStatusLabels(), ['class' => 'form-control']),
    'value' => function ($model) { return User::getStatusLabels($model->status); },
]

5. 時間格式化三種做法

方法程式碼適用場景
閉包格式化'value' => fn($m) => date('Y-m-d', $m->created_at)簡單、一次性
format 陣列'format' => ['date', 'php:Y-m-d'], 'value' => 'created_at'統一格式、可復用
全域 formatter 元件config: 'formatter' => ['dateFormat' => 'yyyy-MM-dd'] → GridView: 'created_at:date'專案層級統一、最乾淨

6. 超連結與圖片欄位

[
    'attribute' => 'id',
    'value' => function ($model) {
        return Html::a($model->id, ['user/view', 'id' => $model->id], ['class' => 'profile-link', 'target' => '_blank']);
    },
    'format' => 'raw', // 關鍵:不轉義 HTML
]

7. 關聯表欄位顯示與搜尋排序

模型定義關聯:public function getOrder() { return $this->hasOne(Order::class, ['id' => 'order_id']); }

GridView 直接用 'order.customer_name' 顯示。

搜尋/排序需在 SearchModel 中:

// rules() 加入 'order.customer_name'
public function search($params) {
    $query = self::find()->joinWith('order');
    $dataProvider = new ActiveDataProvider(['query' => $query]);
    $dataProvider->sort->attributes['order.customer_name'] = [
        'asc' => ['order.customer_name' => SORT_ASC],
        'desc' => ['order.customer_name' => SORT_DESC],
    ];
    $query->andFilterWhere(['like', 'order.customer_name', $this->order_customer_name]);
    // ...
}

8. 自訂 ActionColumn 按鈕

[
    'class' => 'yii\grid\ActionColumn',
    'header' => '操作',
    'headerOptions' => ['width' => '120'],
    'template' => '{view} {update} {delete} {forbid}',
    'buttons' => [
        'forbid' => function ($url, $model) {
            return Html::a('', ['user/forbid', 'id' => $model->id]);
        },
    ],
]

kartik-v/yii2-grid 擴展:企業級功能增強

🔗 GitHub | Demo

安裝與 PDF 相依性

composer require kartik-v/yii2-grid "@dev"
# 若報錯缺少 mpdf,暫時關閉導出功能:
// GridView::widget(['export' => false, ...])
# 或安裝:composer require kartik-v/yii2-mpdf "@dev"

核心增強功能

  • EditableColumn:列內直接編輯(AJAX 存檔)。
  • RadioColumn:單選桿。
  • 固定表頭:'floatHeader' => true,捲動時表頭置頂。
  • 合併篩選列與表頭:'mergeHeader' => true,節省垂直空間。
  • 頁面摘要/總計列:'showPageSummary' => true,欄位設 'pageSummary' => true 或字串標籤。
  • 多格式導出:CSV、Excel、PDF、HTML、JSON、Text。
  • 響應式/懸浮高亮:'responsive' => true, 'hover' => true。

完整配置範例

use kartik\grid\GridView;

echo GridView::widget([
    'dataProvider' => $dataProvider,
    'filterModel' => $searchModel,
    'responsive' => true,
    'hover' => true,
    'floatHeader' => true,
    'showPageSummary' => true,
    'panel' => [
        'heading' => '

用戶管理

', 'before' => '
共 ' . $dataProvider->getTotalCount() . ' 筆
', 'after' => false, ], 'toolbar' => [ '{export}', '{toggleData}', ], 'toggleDataOptions' => [ 'maxCount' => 200, 'confirmMsg' => '共 ' . number_format($dataProvider->getTotalCount()) . ' 筆,確定顯示全部?', ], 'export' => [ 'fontAwesome' => 'fa fa-share-square-o', 'target' => '_blank', 'encoding' => 'UTF-8', // 或 GBK 視 Excel 版本 ], 'exportConfig' => [ GridView::CSV => [ 'label' => '導出 CSV', 'iconOptions' => ['class' => 'text-primary'], 'showHeader' => true, 'showPageSummary' => true, 'filename' => '用戶表_' . date('Y-m-d'), 'alertMsg' => '確定導出 CSV?', 'config' => ['colDelimiter' => ',', 'rowDelimiter' => "\r\n"], ], GridView::EXCEL => [ 'label' => '導出 Excel', 'config' => ['worksheet' => '用戶資料'], ], ], 'columns' => [ ['class' => 'kartik\grid\SerialColumn'], ['class' => 'kartik\grid\CheckboxColumn', 'hiddenFromExport' => true], [ 'attribute' => 'username', 'mergeHeader' => true, 'pageSummary' => '總計', ], [ 'attribute' => 'email', 'mergeHeader' => true, ], [ 'attribute' => 'status', 'filter' => Html::activeDropDownList($searchModel, 'status', User::getStatusLabels(), ['class' => 'form-control']), 'value' => fn($m) => User::getStatusLabels($m->status), 'mergeHeader' => true, ], [ 'class' => 'kartik\grid\ActionColumn', 'template' => '{view} {update} {delete}', 'header' => '操作', 'mergeHeader' => true, ], ], ]);

樣式衝突修正(AdminLTE + kartik GridView)

合併表頭底框線變粗問題:

$this->registerCss(".kv-merged-header { border-bottom: 1px solid #eee !important; }");

常見坑點與解決

問題原因解決
導出 CSV 中文亂碼Excel 預設非 UTF-8用 encoding => 'GBK' 或 UTF-8 with BOM;或改導出 Excel 格式
關聯欄位無法排序未在 dataProvider->sort 定義補上 $dataProvider->sort->attributes['rel.field'] = [...]
mergeHeader 導致篩選輸入框消失CSS 衝突調整 .kv-merged-header 樣式、確保 filter 輸入框可見
floatHeader 在彈窗/側邊欄失效容器 overflow 限制確保 GridView 容器無 overflow:hidden,或設定 floatHeaderOffset

結語

Yii2 GridView 配合 kartik-v/yii2-grid 可滿足 95% 後台表格需求:固定表頭、合併篩選、多格式導出、總計列、編輯列。關鍵在於正確配置 DataProvider 排序、善用 mergeHeader 減少垂直佔用、處理導出編碼相容性。若專案需求極度複雜(如多層表頭、跨欄合併、即時協作),可考慮前端表格庫(AG Grid、Handsontable)配合 API 模式。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved