Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PJAX issue reload #243

Closed
samirmember opened this issue Mar 7, 2015 · 19 comments
Closed

PJAX issue reload #243

samirmember opened this issue Mar 7, 2015 · 19 comments
Labels

Comments

@samirmember
Copy link

Hi Kartik V,
Really great extension, thank you for your efforts
I need help, why my page is refreshing after $.pjax.reload({container:'#w0'});
Here is my grid:

<?= GridView::widget([
    'dataProvider' => $dataProvider,
    'filterModel' => $searchModel,
    'hover' => true,
    'condensed' => true,
    'export' => false,
    'pjax' => true,
    'floatHeader'=>true,
    'columns' => [
        ['class' => 'yii\grid\SerialColumn'],
        [
            'class'       => '\kartik\grid\CheckboxColumn',
            'pageSummary' => true,
            'rowSelectedClass' => GridView::TYPE_SUCCESS,
            'contentOptions'=>['style'=>'width: 0.5%'],
        ],
        [
            'attribute' => 'id_club',
            'contentOptions'=>['style'=>'width: 0.5%'],
        ],
        [
            'format' => ['link', 'Wilaya'],
            'attribute' => 'id_wilaya',
            'filterType'=>GridView::FILTER_SELECT2,
            'filterWidgetOptions' => [
                    'data' => \yii\helpers\ArrayHelper::map(app\models\Wilaya::find()->all(), 'id_wilaya', 'nom_wilaya'),
                    'options' => ['placeholder' => 'Wilaya'],
                    'pluginOptions' => ['allowClear' => true],
            ],
        ],
        [
            'format' => ['link', 'Division'],
            'attribute' => 'id_division',
        ],
        'nom_club',
        'abrev_club',
        'email_club:email:email',
        [
            'class' => 'kartik\grid\BooleanColumn',
            'attribute' => 'etat_club', 
            'vAlign' => 'middle',
        ],
        [
            'class' => 'yii\grid\ActionColumn', 
            'headerOptions' => ['width' => '80'],
            'template' => '{view} {update} {delete}',
        ],
    ],
]); ?>

And here is my button:

echo Html::a(Icon::show('trash') . 'Supprimer','club/bulk-delete', [
    'class' => 'btn btn-danger',
    'id' => 'bulk_delete',
    'model' => 'club',
    'data-confirm' => 'Êtes-vous sûre de vouloir supprimer ces élements?',
]);

And here is my js:

// BULK DELETE
$('#bulk_delete').on('click',function() {
    var model = $(this).attr('model');
    var pks = $('#w0').yiiGridView('getSelectedRows');
    if (!pks || 0 !== pks.length) {
        yii.confirm = function(message, ok, cancel) {
            bootbox.confirm(message, function(result) {
                if (result) {
                    $.ajax({
                       url: 'bulk-delete',
                       data: {id: pks},
                       success: function(data) {
                            $.pjax.reload({container:'#w0'});
                       }
                    });
                } else { !cancel || cancel(); }
            });
        }
    } else {
        bootbox.alert("Aucune ligne sélectionnée<br/>Veuillez sélectionner au moins un enregistrement!");
        return false;
    }
});
@kartik-v
Copy link
Owner

kartik-v commented Mar 8, 2015

Not related to the extension -- its more to do with your markup - that you need to debug.

For example, I would try replacing the Html::a to a Html::button to ensure that page redirection does not happen. For example:

echo Html::button(Icon::show('trash') . 'Supprimer', [
    'type' => 'button',
    'class' => 'btn btn-danger',
    'id' => 'bulk_delete',
    'model' => 'club',
    'data-url' => ''club/bulk-delete', 
    'data-confirm' => 'Êtes-vous sûre de vouloir supprimer ces élements?',
]);

and use the data-url in the button to build your javascript while trapping the click event of the button.

If you need to use Html::a you need to use a event.preventDefault somewhere.

@kartik-v kartik-v closed this as completed Mar 8, 2015
@samirmember
Copy link
Author

Hi Kartik-V,
Thanks for your response.
Unfortunately this doesn't work for me. The page is always refreshing with Html::button or Html::a using event.preventDefault
When I use the yii\grid\GridView, my pjax works fine.
Can you tell me how or where can I debug this issue please.

@kartik-v
Copy link
Owner

kartik-v commented Mar 9, 2015

The default yii\grid\GridView has no pjax setup inbuilt. You need to setup your PJAX widget separately and GridView separately.

In kartik\grid\GridView, the pjax rendering is inbuilt when you set pjax property to true. You can control the pjax container identifier through pjaxSettings property. Read about pjax in kartik\grid\GridView documentation.

What you need to check:

  • Are you having a separate PJAX wrapper widget in addition to one generated by kartik\grid\GridView? This will be triggering two different pjax reloads... when you call pjax reload?

Since I cannot replicate your situation on my tests... you may need to debug by adding functionality one by one on your environment. Start with a simple kartik\grid\gridview without any other elements on the page and without loading other grid plugins like export etc... and try a simple pjax reload and then proceed from there.

@samirmember
Copy link
Author

Hi Kartik-V,
I'll try to do so! When I'll find the solution, I'll post it here in case.
Thanks again for your time

@samirmember
Copy link
Author

Hi Krajee,
I've made a lot of tests, and debugged step by step, but it's always refreshing the page.
I've also used a fresh yii2 advanced template, and added \kartik\grid\Module module but the problem is still the same: when I execute this

jQuery.pjax.reload({container:'#w0'});

My page is reloaded on any index View. Please, can you test this from your side?

@kartik-v
Copy link
Owner

I think the container identifier for pjax is wrong - you need to check the markup.

Note that PJAX container for yii2-grid is set via pjaxSettings['options']['id']. This defaults to $grid->options['id'] . '-pjax' where $grid->options['id'] is the identifier for the grid.

You can override this by manually setting your own pjaxSettings['options']['id'].

This is highlighted in the documentation.

@samirmember
Copy link
Author

Oh YES! Now it works fine!!!
I've only added the pjaxSettings['options']['id']
I didn't know that this step was mandatory
A great thanks for you.

@kartik-v
Copy link
Owner

You are welcome.

Note this step is not mandatory for most cases. But if you need to trigger your own custom pjax reload you will need the same pjax container id that is consistent within pjaxSettings in yii2-grid. In those cases you may need to set this.

@samirmember
Copy link
Author

Ok, now I got it

@astralliquid
Copy link

Hi,

I am having the same problem and try as I may, I do not understand the solution stated above. Here are codes :

view/index.php

  $js = "$('#downloadSelected').on('click',function() {
            $.post(
                \"delete-multiple\", {
                    pk : $('#w0').yiiGridView('getSelectedRows')
                },
                function () {
                    $.pjax.reload({container:'#w0-container'});
                }
            );
        });
";
$this->registerJs($js, $this::POS_READY);

 echo GridView::widget([
    'dataProvider' => $dataProvider,
    'columns' => $gridColumns,
    'containerOptions' => ['style'=>'overflow: auto',], // only set when $responsive = false
    'headerRowOptions'=>['class'=>'kartik-sheet-style'],
    'filterRowOptions'=>['class'=>'kartik-sheet-style'],
    'pjax' => true, // pjax is set to always true for this demo
    'pjaxSettings' =>[
        'neverTimeout'=>true,
        'options'=>[
                'id'=>'w0',
            ]
        ],  
    'beforeHeader'=>[
        [
        'columns'=>[
        ['content'=>'Header Before 1', 'options'=>['colspan'=>5, 'class'=>'text-center warning']],
        ['content'=>'Header Before 2', 'options'=>['colspan'=>3, 'class'=>'text-center warning']],
        ['content'=>'Header Before 3', 'options'=>['colspan'=>3, 'class'=>'text-center warning']],
        ],
        'options'=>['class'=>'skip-export'] // remove this row from export
        ]
    ],

    // set your toolbar
    'toolbar' => [
    ['content'=>
    Html::button('<i class="glyphicon glyphicon-plus"></i>', ['type'=>'button', 'title'=>Yii::t('app', 'Add Book'), 'class'=>'btn btn-success', 'onclick'=>'alert("This will launch the book creation form.\n\nDisabled for this demo!");']) . ' '.
    Html::a('<i class="glyphicon glyphicon-repeat"></i>', ['grid-demo'], ['data-pjax'=>0, 'class' => 'btn btn-default', 'title'=>Yii::t('app', 'Reset Grid')])
    ],
    ],
    // parameters from the demo form
    'panel' => [
    'type' => GridView::TYPE_PRIMARY,
    'heading' => 'heading',
     'after'=>'<div class="pull-right"><button type="button" class="btn btn-primary" id="downloadSelected"><i class="glyphicon glyphicon-download-alt"></i> Download Selected</button></div><div style="padding-top: 5px;"><em>* The page summary displays SUM for first 3 amount columns and AVG for the last.</em></div>',
        ],
    'persistResize' => false,
    ]);

I am confused how to set the #w0 or #w0-pjax or #w0-container.. The code above reload the grid, afterwhich, it refresh the whole page again. If I change the #w0-container in pjax.reload to #w0 like this :

$js = "$('#downloadSelected').on('click',function() {
            $.post(
                \"delete-multiple\", {
                    pk : $('#w0').yiiGridView('getSelectedRows')
                },
                function () {
                    $.pjax.reload({container:'#w0'});
                }
            );
        });
";

It calls the delete-multple function and did not refresh the page. But subsequently the button is not functioning anymore. Nothing happens after the first click.

Please help.

@kartik-v
Copy link
Owner

Do not duplicate identifiers for HTML elements.

The pjax container id and grid id are identifiers for two different HTML elements and you cannot keep them same.

Check your generated HTML markup - you must have unique identifiers (the w0 above must not be duplicated).

Pjax container id is set via pjaxSettings['options']['id']. It must be different than the grid identifier.

Check with something like this:

pjaxSettings['options']['id'] = `kv-unique-id-1';

And in your pjax reload

function () {
   $.pjax.reload({container:'#kv-unique-id-1'});
}

@astralliquid
Copy link

Hi Kartik
Thanks for the reply.. I did as you told, the button works the first time showing the loading.gif and seems like refreshing the grid and not reloading the whole page. But after that, the button cannot click anymore.. it won't fresh the grid or show the loading.gif again, nothing happens.

Sorry, I am very new to yii codes and need detailed help...can you please confirm if :

pjaxSettings['options']['id'] = `kv-unique-id-1';

is the same as

    'filterRowOptions'=>['class'=>'kartik-sheet-style'],
    'pjax' => true, // pjax is set to always true for this demo
    'pjaxSettings' =>[
        'neverTimeout'=>true,
        'options'=>[
                'id'=>'kv-unique-id-1',
            ]
        ],  
    'beforeHeader'=>[

how and where should I put this line you mentioned

pjaxSettings['options']['id'] = `kv-unique-id-1';

The grid generated is

 <div id="kv-unique-id-1">
    <div id="w0" class="grid-view" data-krajee-grid="kvGridInit_120f2538">
      <div class="panel panel-primary">    
        <div class="panel-heading">    
          ...
        </div>    
        <div class="kv-panel-before">    
          <div class="pull-right">        
           ....       
          </div>         
          <div class="clearfix">
          </div>
        </div>    
        <div id="w0-container" class="table-responsive kv-grid-container" style="overflow: auto">
          <table class="kv-grid-table table table-bordered table-striped">
            <colgroup>
            ...
            <col>
            </colgroup>
            <thead>
              <tr class="skip-export">  
               ...
              </tr>
              <tr class="kartik-sheet-style">
                ...
              </tr>
            </thead>
            <tbody>
              <tr data-key="10">
                ...
              </tr>
              <tr data-key="12">
               ...
              </tr>
            </tbody>
          </table>
        </div>    
        <div class="kv-panel-after">
          <div class="pull-right">
            <button type="button" class="btn btn-primary" id="downloadSelected">
              <i class="glyphicon glyphicon-download-alt"></i> Download Selected
            </button>
          </div>
          <div style="padding-top: 5px;">
           ...
          </div>
        </div>    
        <div class="panel-footer">    
         ...
        </div>
      </div>
    </div>
  </div>      

the script generated is

<script type="text/javascript">jQuery(document).ready(function () {
$('#downloadSelected').on('click',function() {
            $.post(
                "delete-multiple", {
                    pk : $('#w0').yiiGridView('getSelectedRows')
                },
                function () {
                    $.pjax.reload({container:'#kv-unique-id-1'});
                }
            );
        });

kvSelectRow("w0", "danger");
var kvGridInit_120f2538=function(){
$('#w0 .export-html').gridexport(kvGridExp_753617e1);$('#w0 .export-csv').gridexport(kvGridExp_be83543c);$('#w0 .export-txt').gridexport(kvGridExp_62d1b906);$('#w0 .export-xls').gridexport(kvGridExp_84466b9d);$('#w0 .export-pdf').gridexport(kvGridExp_e76978c2);$('#w0 .export-json').gridexport(kvGridExp_ad8d691d);$('#w0-container').resizableColumns({store:null});
}
kvGridInit_120f2538();
jQuery('#w1').button();
jQuery("#kv-unique-id-1").on('pjax:timeout', function(e){e.preventDefault()}).on('pjax:send', function(){jQuery("#w0-container").addClass('kv-grid-loading')}).on('pjax:complete', function(){setTimeout(kvGridInit_120f2538(), 2500);jQuery("#w0-container").removeClass('kv-grid-loading');});
jQuery('#w0').yiiGridView({"filterUrl":"/yii/1realty.com/public_html/beta/property/index","filterSelector":"#w0-filters input, #w0-filters select"});
jQuery('#w0').yiiGridView('setSelectionColumn', {"name":"selection[]","multiple":true,"checkAll":"selection_all"});
jQuery("#kv-unique-id-1").on('pjax:complete', function(){kvSelectRow('w0', 'danger');});
jQuery(document).pjax("#kv-unique-id-1 a", "#kv-unique-id-1", {"push":true,"replace":false,"timeout":1000,"scrollTo":false});
jQuery(document).on('submit', "#kv-unique-id-1 form[data-pjax]", function (event) {jQuery.pjax.submit(event, '#kv-unique-id-1', {"push":true,"replace":false,"timeout":1000,"scrollTo":false});});
});</script>

@astralliquid
Copy link

Yes I Got it to work!! The problem is I put the button inside the pjax container where it should be outside.

this kartik-v/yii2-widgets#202 helps me

Pjax will overwrite the entire grid content DOM and hence you need to reinitialize select2 jquery plugin since it lies within the grid DOM.

    OPTION 1: You can render the Select2 widget outside the grid container... this should be an easy fix -- but it may mean your UI design will not be the way you want OR

Thanks to Kartik

@Ma-ve
Copy link

Ma-ve commented Oct 17, 2015

For anyone else who has had an issue with this: my problem was that I had a button inside the Pjax view, and I bound it to the class itself. But, after the first click, the content is reloaded, so the hard link to the button no longer exists*. Use $('body').on('click', '.your-class', function(){});

*fixed typo

@wanzhongyi
Copy link

Ma-ve 👍 Very good ,thank you

@hassansheikh
Copy link

Hi,
I am using $.pjax.reload({ container: '#healthcare-crud' }); to update the grid after deleting. Problem is that when i am on page=2 of the grid then delete a record on this page after refreshing the grid it comes to me at page=1. It should stay on the same page=2 after grid update.

Please reply me ASAP.

Thanks in advanced :)

@dogrocker
Copy link
Contributor

Thanks, @Ma-ve.

@hAppywAy
Copy link

hAppywAy commented Nov 4, 2016

Thanks, @Ma-ve. Made my day !

@blacksesion
Copy link

Very thanks @Ma-ve , you save me!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

9 participants