在yii2中使用网格外部的select2小部件过滤gridview

时间:2016-08-17 21:41:53

标签: yii2

我正在尝试通过select2小部件过滤网格视图。但是select2小部件不应该在gridview中。就像截图一样 - enter image description here 当我选择select2小部件时,数据被过滤。 我的index.php代码是 -

<?php

use yii\helpers\Html;
use yii\grid\GridView;
use kartik\select2\Select2;
use yii\helpers\ArrayHelper;
use frontend\modules\productstockbook\models\Productnames;
use yii\helpers\Json;

/* @var $this yii\web\View */
/* @var $searchModel frontend\modules\productstockbook\models\ProductionSearch */
/* @var $dataProvider yii\data\ActiveDataProvider */

$this->title = 'Product Stock Book';
$this->params['breadcrumbs'][] = $this->title;
?>
<div class="production-index">

    <h1><?= Html::encode($this->title) ?></h1>
    <?php // echo $this->render('_search', ['model' => $searchModel]); ?>

    <?php
        echo Select2::widget([
        'model' => $model,
        'attribute' => 'productnames_productname',
        'data' => ArrayHelper::map(Productnames::find()->all(),'productnames_productname','productnames_productname'),
        'options' => ['placeholder' => 'Select Product', 'id' => 'catid'],
        'pluginOptions' => [
            'allowClear' => true
        ],
        ]);
    ?>
    <div class="row-fluid">
        <div class="form-group">
            <div class="col-xs-3 col-sm-3 col-lg-3" >
                    <input type="text" class="form-control" id="production" readonly placeholder ="Production">                
            </div>
            <div class="col-xs-3 col-sm-3 col-lg-3" >
                    <input type="text" class="form-control" id="sell" readonly placeholder ="Sell">                
            </div>
            <div class="col-xs-3 col-sm-3 col-lg-3" >
                    <input type="text" class="form-control" id="stock" readonly placeholder ="Stock">                
            </div>
            <div class="col-xs-3 col-sm-3 col-lg-3" >
                    <button type="button" id="search" class="btn btn-primary"><span class="glyphicon glyphicon-search" aria-hidden="true"></span></button>
            </div>
        </div>
    </div>
    <div class= 'col-md-6'>
    <?= GridView::widget([
        'dataProvider' => $dataProvider,
        'filterModel' => $searchModel,
        'columns' => [
            ['class' => 'yii\grid\SerialColumn'],

            //'productionid',
            'productiondate',
            //'itemid',
            'productname',
            //'batchno',
            'prodqty',

            //['class' => 'yii\grid\ActionColumn'],
        ],
    ]); ?>
</div>

<div class='col-md-6'>

    <?php
        echo GridView::widget([
        'dataProvider' => $dataProvider2,
        'filterModel' => $searchModel2,
        'columns' => [
            ['class' => 'yii\grid\SerialColumn'],

            'billdate',
            'productsales_partyname',
            'productname',
            'total',

        ], 
        ]); 
      ?>
  </div>
</div>


<?php
/* start getting the textboxes */
$script = <<< JS
$(function(){
    //$(document).ready(function(e) { getTotalproduction(); });

    $('#catid').change(function(){   
        getIndexpage();
        //getTotalproduction();
        //getTotalsell();
        //getTotalstock();
    });

    var catid = $(this).val();

    var getIndexpage = function(){        
        var catid = String($('#catid').val());
        window.onbeforeunload = function(e) {return getTotalproduction();};
        window.location.href = 'index.php?r=productstockbook/production/index&catid='+catid;       

    } ;
    var getTotalproduction = function(){        
        var catid = String($('#catid').val());
        $.get('index.php?r=productstockbook/production/get-for-production',{ catid : catid }, function(data){
        //alert(data);
        var data = $.parseJSON(data);
        $('#production').attr('value',data.totalproduction);
    }); 

    } ;
    var getTotalsell = function(){        
        var catid = String($('#catid').val());
        $.get('index.php?r=productstockbook/production/get-for-sales',{ catid : catid }, function(data){
        //alert(data);
        var data = $.parseJSON(data);
        $('#sell').attr('value',data.totalsell);
    });

    };
    var getTotalstock = function(){        

        var totalproduction = parseInt($('#production').val());
        var totalsell = parseInt($('#sell').val());
        var totalstock = Math.round(totalproduction - totalsell)

        //alert(totalstock);
        if (isNaN(totalstock) || totalstock < -10000000 || totalstock > 1000000) {
        totalstock = '';
        }
        $('#stock').val(totalstock);
    };
    // var getTotalstock = function(){        

    //     var catid = String($('#catid').val());
    //     $.get('index.php?r=productstockbook/production/get-for-stock',{ catid : catid }, function(data){
    //     alert(data);
    //     var data = $.parseJSON(data);
    //     $('#stock').attr('value',data.stock);
    // });
    // };
});


JS;
$this->registerJs($script);
/* end getting the textboxes */
?>

我的控制器代码是 -

<?php

namespace frontend\modules\productstockbook\controllers;

use Yii;
use frontend\modules\productstockbook\models\Production;
use frontend\modules\productstockbook\models\ProductionSearch;
use yii\web\Controller;
use yii\web\NotFoundHttpException;
use yii\filters\VerbFilter;
use frontend\modules\productstockbook\models\ProductsalesSearch;
use yii\helpers\Html;
use frontend\modules\productstockbook\models\Productnames;
use frontend\modules\productstockbook\models\Productsales;
use yii\helpers\Json;
use yii\db\Query;
use yii\db\Command;

/**
 * ProductionController implements the CRUD actions for Production model.
 */
class ProductionController extends Controller
{
    /**
     * @inheritdoc
     */
    public function behaviors()
    {
        return [
            'verbs' => [
                'class' => VerbFilter::className(),
                'actions' => [
                    'delete' => ['POST'],
                ],
            ],
        ];
    }

    /**
     * Lists all Production models.
     * @return mixed
     */
    public function actionIndex()
    {
        $catid = yii::$app->request->get('catid');
        $searchModel = new ProductionSearch();
        $dataProvider = $searchModel->search(Yii::$app->request->queryParams, $catid);
        $searchModel2 = new ProductsalesSearch();
        $dataProvider2 = $searchModel2->search(Yii::$app->request->queryParams, $catid);
        $model = new Productnames();
        return $this->render('index', [
            'searchModel' => $searchModel,
            'dataProvider' => $dataProvider,
            'searchModel2' => $searchModel2,
            'dataProvider2' => $dataProvider2,
            'model' => $model,
        ]);
    }

    /**
     * Displays a single Production model.
     * @param integer $id
     * @return mixed
     */
    public function actionView($id)
    {
        return $this->render('view', [
            'model' => $this->findModel($id),
        ]);
    }

    /**
     * Creates a new Production model.
     * If creation is successful, the browser will be redirected to the 'view' page.
     * @return mixed
     */
    public function actionCreate()
    {
        $model = new Production();

        if ($model->load(Yii::$app->request->post()) && $model->save()) {
            return $this->redirect(['view', 'id' => $model->productionid]);
        } else {
            return $this->render('create', [
                'model' => $model,
            ]);
        }
    }

    /**
     * Updates an existing Production model.
     * If update is successful, the browser will be redirected to the 'view' page.
     * @param integer $id
     * @return mixed
     */
    public function actionUpdate($id)
    {
        $model = $this->findModel($id);

        if ($model->load(Yii::$app->request->post()) && $model->save()) {
            return $this->redirect(['view', 'id' => $model->productionid]);
        } else {
            return $this->render('update', [
                'model' => $model,
            ]);
        }
    }

    /**
     * Deletes an existing Production model.
     * If deletion is successful, the browser will be redirected to the 'index' page.
     * @param integer $id
     * @return mixed
     */
    public function actionDelete($id)
    {
        $this->findModel($id)->delete();

        return $this->redirect(['index']);
    }

    /**
     * Finds the Production model based on its primary key value.
     * If the model is not found, a 404 HTTP exception will be thrown.
     * @param integer $id
     * @return Production the loaded model
     * @throws NotFoundHttpException if the model cannot be found
     */
    protected function findModel($id)
    {
        if (($model = Production::findOne($id)) !== null) {
            return $model;
        } else {
            throw new NotFoundHttpException('The requested page does not exist.');
        }
    }
    public function actionGetForProduction($catid)
    {
        $production = Production::find()->select('sum(prodqty) as totalproduction')->where(['productname'=>$catid])->asArray()->one();
        echo Json::encode($production);
    }

    public function actionGetForSales($catid)
    {
        $sell = Productsales::find()->select('sum(total) as totalsell')->where(['productname'=>$catid])->asArray()->one();
        echo Json::encode($sell);
    }
    // public function actionGetForStock($catid)
    // {
    //     //$stock = Productsales::find()->joinWith('Production')->select('sum(production.prodqty) - sum(productsales.total) as stock')->where(['productname'=>$catid])->asArray()->one();
    //     //echo Json::encode($stock);
    //     //$subQuery1 = (new Query())->select(['productname,sum(prodqty) as totalproduction'])->from('production')->where(['productname'=>$catid]);
    //     $subQuery2 = (new Query())->select(['productname,sum(total) as totalsell'])->from('productsales')->where(['productname'=>$catid]);
    //     $subQuery3 = (new Query())->select(['productname,(sum(prodqty) - sell.totalsell) as totalstock'])->from('production')->leftJoin(['sell' => $subQuery2],'sell.productname = productname')->where(['productname'=>$catid]);
    //     echo Json::encode($subQuery3);
    // }

}

ProductionSearch模型代码 -

<?php

namespace frontend\modules\productstockbook\models;

use Yii;
use yii\base\Model;
use yii\data\ActiveDataProvider;
use frontend\modules\productstockbook\models\Production;

/**
 * ProductionSearch represents the model behind the search form about `frontend\modules\productstockbook\models\Production`.
 */
class ProductionSearch extends Production
{
    /**
     * @inheritdoc
     */
    public function rules()
    {
        return [
            [['productionid', 'itemid', 'prodqty'], 'integer'],
            [['productiondate', 'productname', 'batchno'], 'safe'],
        ];
    }

    /**
     * @inheritdoc
     */
    public function scenarios()
    {
        // bypass scenarios() implementation in the parent class
        return Model::scenarios();
    }

    /**
     * Creates data provider instance with search query applied
     *
     * @param array $params
     *
     * @return ActiveDataProvider
     */
    public function search($params,$catid)
    {
        $query = Production::find()
                //->select(['productionid', 'productiondate', 'itemid', 'productname', 'batchno', 'prodqty'])
                ->orDerBy([
                        'productiondate'=>SORT_DESC,
                    ])
                ->andWhere(['productname' => $catid]);
        // add conditions that should always apply here

        $dataProvider = new ActiveDataProvider([
            'query' => $query,
        ]);

        $this->load($params);

        if (!$this->validate()) {
            // uncomment the following line if you do not want to return any records when validation fails
            // $query->where('0=1');
            return $dataProvider;
        }

        // grid filtering conditions
        $query->andFilterWhere([
            'productionid' => $this->productionid,
            'productiondate' => $this->productiondate,
            'itemid' => $this->itemid,
            'prodqty' => $this->prodqty,
        ]);

        $query->andFilterWhere(['like', 'productname', $this->productname])
            ->andFilterWhere(['like', 'batchno', $this->batchno]);

        return $dataProvider;
    }
}

ProductsalesSearch Model Code -

<?php

namespace frontend\modules\productstockbook\models;

use Yii;
use yii\base\Model;
use yii\data\ActiveDataProvider;
use frontend\modules\productstockbook\models\Productsales;

/**
 * ProductsalesSearch represents the model behind the search form about `frontend\modules\productstockbook\models\Productsales`.
 */
class ProductsalesSearch extends Productsales
{
    /**
     * @inheritdoc
     */
    public function rules()
    {
        return [
            [['id', 'productsales_ebillid', 'discount'], 'integer'],
            [['year', 'console', 'billno', 'billdate', 'productsales_partyname', 'itemid', 'productname', 'batchno', 'expdate', 'productiondate', 'prodqty', 'qty', 'free', 'total'], 'safe'],
            [['mrp', 'rate'], 'number'],
        ];
    }

    /**
     * @inheritdoc
     */
    public function scenarios()
    {
        // bypass scenarios() implementation in the parent class
        return Model::scenarios();
    }

    /**
     * Creates data provider instance with search query applied
     *
     * @param array $params
     *
     * @return ActiveDataProvider
     */
    public function search($params,$catid)
    {
        $query = Productsales::find()

                ->orDerBy([
                        'billdate'=>SORT_DESC,
                    ])
                ->andWhere(['productname' => $catid]);
        // add conditions that should always apply here

        $dataProvider = new ActiveDataProvider([
            'query' => $query,
        ]);

        $this->load($params);

        if (!$this->validate()) {
            // uncomment the following line if you do not want to return any records when validation fails
            // $query->where('0=1');
            return $dataProvider;
        }

        // grid filtering conditions
        $query->andFilterWhere([
            'id' => $this->id,
            'productsales_ebillid' => $this->productsales_ebillid,
            'billdate' => $this->billdate,
            'expdate' => $this->expdate,
            'mrp' => $this->mrp,
            'rate' => $this->rate,
            'productiondate' => $this->productiondate,
            'discount' => $this->discount,
        ]);

        $query->andFilterWhere(['like', 'year', $this->year])
            ->andFilterWhere(['like', 'console', $this->console])
            ->andFilterWhere(['like', 'billno', $this->billno])
            ->andFilterWhere(['like', 'productsales_partyname', $this->productsales_partyname])
            ->andFilterWhere(['like', 'itemid', $this->itemid])
            ->andFilterWhere(['like', 'productname', $this->productname])
            ->andFilterWhere(['like', 'batchno', $this->batchno])
            ->andFilterWhere(['like', 'prodqty', $this->prodqty])
            ->andFilterWhere(['like', 'qty', $this->qty])
            ->andFilterWhere(['like', 'free', $this->free])
            ->andFilterWhere(['like', 'total', $this->total]);

        return $dataProvider;
    }
     // public function gettotalProduction()
     //    {
     //            return $this->c_name.' - '.$this->c_address.' - '.$this->c_mobileno;
     //    }
}

我的观点是,在index.php文件中的javascript中使用了以下代码 -

window.location.href = 'index.php?r=productstockbook/production/index&catid='+catid;

我不希望重新定位页面。因为如果它重新定位,我不能在文本框中得到sum(prodqty)和sum(total),正如你在页面中看到的那样,页面正被重新定位。如何在不重新定位页面的情况下实现此目的?这是与Filter data with kartik Select2 widget in gridview

相同的问题

更新
目前在研究Edvin的解决方案后 - 我面临以下错误 - enter image description here

1 个答案:

答案 0 :(得分:0)

因为我看到它已经过滤了数据(但是页面重新加载),所以我转到第2部分,你要求提供特定列的总和。

目前我无法想出更好的解决方案,但现在应该可行。请注意,它可能只是临时解决方案,因为此代码是&#34;脆弱的&#34; (添加一个额外的列,更改表和ID等)将破坏这一点,您将被迫修改此代码。另请注意,它需要所有打印行的总和(意味着只计算可见(默认为1st))。

我之前使用过类似的东西,因为ID有点静态,很少会让我失望。

$(document).on('ready', function(e) {
        var row0 = $('#w0')[0]['childNodes'][2]['childNodes'][2]['children'];
        var row1 = $('#w1')[0]['childNodes'][2]['childNodes'][2]['children'];
        var total0 = 0;
        var total1 = 0;

        for (var i = 0; i < row0.length; i++) {
            total0 += parseInt(row0[i]['children'][3]['textContent'], 10);
        }

        for (var i = 0; i < row1.length; i++) {
            total1 += parseInt(row1[i]['children'][4]['textContent'], 10);
        }
                                                // ^ This number takes (n+1)th column
        console.log('First table total value: ' + total0);
        console.log('Second table total value: ' + total1);
        console.log('Difference between 1st and 2nd total values: ' + (total0 - total1));
    })

这将有效,假设你的桌子&#39; ID是&#34; w0&#34; (第一张表)和&#34; w1&#34; (第二个表格),您所代表的图片中确实存在相应数量的列。

如果有大量记录,您可以通过在模型中添加其他行来增加要在表中打印的行数:

$dataProvider = new ActiveDataProvider([
            'query' => $query,
            'pagination' => [
                'pageSize' => 30,
            ]
        ]);