2011-05-12 16 views
17

sto usando il DataTables jQuery Plugin e avere una configurazione click gestore nel braccio scatto nel modo seguente:jQuery DataTable - Row non cliccare registrarsi a pagine diverse da prima

$('#dt tbody tr').click(function() { 
     alert('e'); 
}); 

Questo funziona perfettamente per la prima pagina dei risultati DataTable .

Tuttavia, quando si passa a un'altra pagina di risultati, il gestore di clic non registra più.

La mia presunzione è che il codice DataTables stia fermando la propagazione dell'evento click al gestore, ma poiché ciò si verifica solo sulle pagine dopo il primo, sembra insolito.

come tale, ha nessuno:

  1. incontrato (e idealmente risolto) il problema
  2. trovato un buon modo per tenere traccia jQuery/JS propagazione evento per isolare il motivo per cui l'evento è stato arrestato

Cheers

+0

La mia presunzione non era corretto. Un'altra presunzione non dichiarata: il legame in 'ajaxComplete' si legherebbe a tutte le righe, non era valido in quanto DataTables è saggio e non esegue il rendering di tutte le righe nel browser fino a quando non è richiesto. In quanto tale, la risposta di Kon 'live()' è corretta. –

+0

Si prega di guardare la risposta fornita da Chris Everitt. Usa una funzione DataTables integrata e NON usa funzioni jquery deprecate. – Nullius

risposta

11

Ho riscontrato questo problema in un'applicazione a pagina singola. Il metodo live ha funzionato per me eccetto dopo un postback. La mia tabella è stata popolata tramite ajax e l'utente potrebbe causarne la distruzione e la ricreazione.

Per risolvere il problema ho usato DataTables $:. "http://datatables.net/api#$"

Ecco il mio fix utilizzando l'esempio DataTables danno per la funzione riga nascosta.

$(document).ready(function() { 
    /* 
    * Insert a 'details' column to the table 
    */ 
    var nCloneTh = document.createElement('th'); 
    var nCloneTd = document.createElement('td'); 
    nCloneTd.innerHTML = '<img src="../examples_support/details_open.png">'; 
    nCloneTd.className = "center"; 

    /* CHANGE: Remove all the expand control elements we may have added earlier 
    * or else you'll add a new column for every postback 
    */ 
    $('.expand-control').remove(); 

    /* 
    * CHANGE: Add the expand-control class to these elements, 
    * so we can remove them after a postback 
    */ 
    $(nCloneTh).addClass('expand-control'); 
    $(nCloneTd).addClass('expand-control'); 

    $('#example thead tr').each(function() { 
     this.insertBefore(nCloneTh, this.childNodes[0]); 
    }); 

    $('#example tbody tr').each(function() { 
     this.insertBefore( nCloneTd.cloneNode(true), this.childNodes[0]); 
    }); 

    /* 
    * Initialse DataTables, with no sorting on the 'details' column 
    */ 
    var oTable = $('#example').dataTable({ 
     "aoColumnDefs": [ 
      { "bSortable": false, "aTargets": [ 0 ] } 
     ], 
     "aaSorting": [[1, 'asc']] 
    }); 

    /* Add event listener for opening and closing details 
    * Note that the indicator for showing 
    * which row is open is not controlled by DataTables, 
    * rather it is done here 
    */ 

    /* CHANGE: Here I use jQuery.dataTable.$ instead of 
    * jQuery('#example tbody td img'), 
    * this is what preserves the event handler on the 2nd (etc) 
    * pages after a postback 
    * Note the use of on instead of live, recommended over live as of 1.7 
    */ 
    oTable.$('tr').find('img').on('click', function() { 
     var nTr = $(this).parents('tr')[0]; 
     if (oTable.fnIsOpen(nTr)) 
     { 
      /* This row is already open - close it */ 
      this.src = "../examples_support/details_open.png"; 
      oTable.fnClose(nTr); 
     } 
     else 
     { 
      /* Open this row */ 
      this.src = "../examples_support/details_close.png"; 
      oTable.fnOpen(nTr, fnFormatDetails(oTable, nTr), 'details'); 
     } 
    }); 
}); 
+0

Questa dovrebbe essere la risposta accettata L'uso di funzioni deprecate come jquery live() non è mai una buona idea, basta usare tableVariable. $ ('tr') invece di $ ('# tableId tr') come te +1 – Nullius

+0

Aggiornato, grazie –

+0

Questo ha risolto anche il mio problema simile quando provavo ad usare una tecnica suggerito su questo post del blog: http://ricardocovo.com/2010/09/02/asp-mvc-delete-confirmation-with-ajax-jquery-ui-dialog/ (cioè, utilizzando la tecnica di dialogo di conferma dell'eliminazione in combinazione con dati jQuery); ... i collegamenti di eliminazione hanno smesso di funzionare sulle pagine dopo la prima pagina; così invece di usare $ ('delete-link'). click (function() etc ..., ho usato l'idea sopra per risolvere il problema, dicendo: oTable. $ ('. delete-link'). on ('click', function() {...}: a quel punto i link di eliminazione hanno iniziato a funzionare di nuovo. –

12

Suppongo che il binding del gestore di eventi venga applicato solo alle righe inizialmente caricate. Ma una volta che la raccolta di righe viene nuovamente sottoposta a revisione nel markup, i gestori di eventi non esistono più.

Controlla la funzione live() di jQuery. La chiave per il fatto che i gestori di eventi sono vincolati per tutti gli elementi che soddisfano i criteri di selezione "ora e in futuro".

+0

Ovviamente, saluti. Strano ha funzionato sulla prima pagina (tutte le righe sono caricate dinamicamente) ma nondimeno penso che questa sia la risposta. Confermerò e accetterò a breve. –

+2

Questo ha senso se si caricano le righe PRIMA di definire il gestore click(). – Kon

+0

Ovviamente, ho inserito il 'click' nel mio gestore' ajaxComplete' pensando che DataTables stia caricando tutte le righe e semplicemente nascondendole. Tuttavia, questo si limita alla prima pagina perché sono tutti i rendering DataTables (il resto viene tenuto in memoria). Rendendolo '$ ('# dt tbody tr') live ('click', function()' ecc. Lo aggiusta (e infatti può essere dichiarato al di fuori di 'ajaxComplete' a causa del bit" now and in the future " menzioni –

5

Ho avuto lo stesso problema con i pulsanti in tutte le mie righe DataTables, l'evento click non ha funzionato su nessun pulsante dopo la prima pagina dei risultati. Kon ha dato l'analisi corretta (grazie Kon), ma per chi cerca codice di esempio, ecco cosa ha funzionato per me:

$('.myButton').live('click', function() { 
    var id = $(this).closest("tr").attr("id"); 
    var string = 'div_id=' + id; 
    alert(string); 
     // string sent to processing script here 
}); 

Sperare che aiuti!

+0

Grazie Codice con la risposta sempre utile – bladefist

+0

grazie funziona perfettamente! – rashid

3

Dato che il live è ora deprecato, suggerisco di usare ".on".

Questo dovrebbe risolvere il problema:

$(document).on('click', '.myButton', function() { 
    var id = $(this).closest("tr").attr("id"); 
    var string = 'div_id=' + id; 
    alert(string); 
     // string sent to processing script here 
}); 

È possibile scambiare documento con qualche elemento principale in quanto non è molto efficiente. Forse prova a usare un div che contiene il tuo tavolo.

1

La mia risposta è simile a quella di @Chris Everitt, con una leggera differenza. Solo per quelli che vorrebbero vederlo .. ecco qui ...

var oTable = $('#masterTable').dataTable({ 

       "aLengthMenu": [[5,10, 25, 50, 100 , -1], [5,10, 25, 50, 100, "All"]], 
       "iDisplayLength" : 10, 
       "aoColumnDefs": [ 
          {"sWidth": "25%", "aTargets": [ 0 ] }, 
          {"sWidth": "10%", "aTargets": [ 1 ] }, 
          {"sWidth": "10%", "aTargets": [ 2 ] }, 
          {"sWidth": "10%", "aTargets": [ 3 ] }, 
          {"sWidth": "10%", "aTargets": [ 4 ] }, 
          {"sWidth": "10%", "aTargets": [ 5 ] }, 
          {"sWidth": "15%", "aTargets": [ 6 ] }, 

          {"sClass": "align-left" , "aTargets": [ 0,1,4, 2,3,5,6] }    
         ], 

      "aoColumns": [ 
       { "bSortable": true }, 
       null, null, null,null, null, 
       { "bSortable": true } 
      ] 

      }); 

Registrazione evento per tutti img (dom attr di) nella tabella -

oTable.$('td').each(function() { 

        $(this).on('click','img', function() { 
         var nTr = $(this).parents('tr')[0]; 
         if (oTable.fnIsOpen(nTr)) 
         { 
          /* This row is already open - close it */ 
          this.src = "${pageContext.request.contextPath}/theme/v_1_0/app-images/details_open.png"; 
          oTable.fnClose(nTr); 
         } 
         else 
         { 
          /* Open this row */ 
          this.src = "${pageContext.request.contextPath}/theme/v_1_0/app-images/details_close.png"; 



          var html = '<div> Placeholder here.. </div>'; 

          oTable.fnOpen(nTr, html, 'details'); 

          } 
        });  
Problemi correlati