在 Kartik Select2 小部件中向下滚动时加载越来越多的数据
Posted
技术标签:
【中文标题】在 Kartik Select2 小部件中向下滚动时加载越来越多的数据【英文标题】:load more and more data when scroll down in Kartik Select2 widget 【发布时间】:2018-12-26 15:30:36 【问题描述】:我正在开发库存管理系统,有大量产品,客户希望在 Select2 小部件中显示产品,就像 kartik 小部件一样,他想在向下滚动时越来越多地表示数据,是吗可用或可以使用此小部件完成,还是我必须创建自己的? 这是我的代码
<?php
$url = Url::to ( [ 'products-list' ] );
echo Select2::widget ( [
'name' => 'state_10' ,
'options' => [
'id' => 'select_product' ,
'placeholder' => 'Select Product...' ,
'multiple' => false ,
'class' => ''
] ,
'pluginOptions' => [
'allowClear' => true ,
'minimumInputLength' => 1 ,
'ajax' => [
'url' => $url ,
'dataType' => 'json' ,
'data' => new JsExpression ( 'function(params) return q:params.term; ' )
] ,
'escapeMarkup' => new JsExpression ( 'function (markup) return markup; ' ) ,
'templateResult' => new JsExpression ( 'function(product) console.log(product);return product.text; ' ) ,
'templateSelection' => new JsExpression ( 'function (subject) return subject.text; ' ) ,
] ,
] );
?>
我的控制器中有这个动作,一切都运行良好,但我需要首先在 select2 中显示一些产品,然后当滚动时开始变得越来越多
控制器动作:
public function actionProductsList($q = null, $id = null)
Yii::$app->response->format = Response::FORMAT_JSON;
$out = ['results' => ['id' => '', 'text' => '', 'qtyLeft' => '', 'serialNumbers' => '']];
if (!is_null($q))
$query = new Query;
$query->select(['product_id as id', new Expression("CONCAT(product_name,' -- ',product_qty_left) AS text, product_qty_left as qtyLeft, s.serial_number as serialNumbers")])
->from('product')
->join('LEFT JOIN', 'serial_number s', 's.r_product_id = product.product_id')
->where(['like', 'product_name', $q]);
// ->limit(20);
$command = $query->createCommand();
$data = $command->queryAll();
$out['results'] = array_values($data);
elseif ($id > 0)
$out['results'] = ['id' => $id, 'text' => AppProduct::find()->where(['product_id' => $id])->one()->product_name];
return $out;
【问题讨论】:
嘿,您需要更新actionProductsList
函数的服务器端代码,请参阅下面我的答案中的更新
你好,非常感谢我遇到了这个问题,导致从数据库中检索到的项目出现冗余,现在我可以说一切都很顺利,谢谢。
【参考方案1】:
根据使用分页的文档,您必须告诉 Select2 通过覆盖 ajax.data
设置将任何必要的分页参数添加到请求中。要检索的当前页面存储在params.page
属性中。
所以你需要把Select2
改成如下
$url = Url::to ( [ 'products-list' ] );
echo Select2::widget ( [
'name' => 'state_10' ,
'options' => [
'id' => 'select_product' ,
'placeholder' => 'Select Product...' ,
'multiple' => false ,
'class' => ''
] ,
'pluginOptions' => [
'allowClear' => true ,
'minimumInputLength' => 1 ,
'ajax' => [
'url' => $url ,
'dataType' => 'json' ,
'data' => new JsExpression ( 'function(params) return q:params.term, page:params.page || 1; ' )
] ,
'escapeMarkup' => new JsExpression ( 'function (markup) return markup; ' ) ,
'templateResult' => new JsExpression ( 'function(product) console.log(product);return product.text; ' ) ,
'templateSelection' => new JsExpression ( 'function (subject) return subject.text; ' ) ,
] ,
] );
Select2 将在响应中期望 pagination.more
值。 more 的值应该是true
或false
,它告诉Select2 是否还有更多页的结果可供检索:
"results": [
"id": 1,
"text": "Option 1"
,
"id": 2,
"text": "Option 2"
],
"pagination":
"more": true
因此修改您的服务器端代码以包含 $page
参数并在您的查询中包含 limit
和 offset
。我目前使用 5 条记录作为限制,您可以更改它。
public function actionProductsList($page, $q = null , $id = null )
$limit=5;
$offset=($page-1)*$limit;
Yii::$app->response->format = Response::FORMAT_JSON;
$out = [ 'results' => [ 'id' => '' , 'text' => '' , 'qtyLeft' => '' , 'serialNumbers' => '' ] ];
if ( !is_null ( $q ) )
$query = new \yii\db\Query;
$query->select ( [ 'product_id as id' , new Expression ( "CONCAT(product_name,' -- ',product_qty_left) AS text, product_qty_left as qtyLeft, s.serial_number as serialNumbers" ) ] )
->from ( 'product' )
->join ( 'LEFT JOIN' , 'serial_number s' , 's.r_product_id = product.product_id' )
->where ( [ 'like' , 'product_name' , $q ] )
->offset ( $offset )
->limit ( $limit );
$command = $query->createCommand ();
$data = $command->queryAll ();
$out['results'] = array_values ( $data );
$out['pagination'] = [ 'more' => !empty($data)?true:false ];
elseif ( $id > 0 )
$out['results'] = [ 'id' => $id , 'text' => AppProduct::find ()->where ( [ 'product_id' => $id ] )->one ()->product_name ];
return $out;
Update
我在上面的代码中发现了一些修复并进行了更改
修复偏移量$offset=($page-1)*$limit;
,而不是使用$page
,如->offset($page)
,使用$offset
,如->offset($offset)
。
正确配置更多结果以在没有更多结果时返回 false,否则即使没有更多结果,它也会继续向服务器发送 ajax 调用,因此请将其更改为 $out['pagination'] = [ 'more' => !empty($data)?true:false ];
【讨论】:
谢谢您,现在一切顺利!感激不尽! 乐于帮助@MohamadaliZayat以上是关于在 Kartik Select2 小部件中向下滚动时加载越来越多的数据的主要内容,如果未能解决你的问题,请参考以下文章
yii2 kartik select2 小部件不显示列表的第一个元素