Ocultar / Mostrar columna en una tabla HTML


Tengo una tabla HTML con varias columnas y necesito implementar un selector de columnas usando jquery. Cuando un usuario hace clic en una casilla de verificación, quiero ocultar / mostrar la columna correspondiente en la tabla. Me gustaría hacer esto sin adjuntar una clase a cada td en la tabla, ¿hay una manera de seleccionar una columna completa usando jquery? A continuación se muestra un ejemplo del HTML.

<table>
    <thead>
        <tr><th class="col1">Header 1</th><th class="col2">Header 2</th><th class="col3">Header 3</th></tr>
    </thead>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
</table>

<form>
    <input type="checkbox" name="col1" checked="checked" /> Hide/Show Column 1 <br />
    <input type="checkbox" name="col2" checked="checked" /> Hide/Show Column 2 <br />
    <input type="checkbox" name="col3" checked="checked" /> Hide/Show Column 3 <br />
</form>
Author: Christopher Rapcewicz, 2009-01-19

9 answers

Me gustaría hacer esto sin adjuntar una clase a cada td

Personalmente, yo iría con el enfoque de la clase-en-cada-td/th/col. A continuación, puede activar y desactivar columnas usando una sola escritura en className en el contenedor, asumiendo reglas de estilo como:

table.hide1 .col1 { display: none; }
table.hide2 .col2 { display: none; }
...

Esto va a ser más rápido que cualquier enfoque de bucle JS; para tablas realmente largas puede hacer una diferencia significativa en la capacidad de respuesta.

Si puede salirse con la suya sin apoyar IE6, podría use selectores de adyacencia para evitar tener que agregar los atributos de clase a tds. O alternativamente, si su preocupación es hacer el limpiador de marcado, podría agregarlos desde JavaScript automáticamente en un paso de inicialización.

 78
Author: bobince,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-19 14:16:12

Una línea de código usando jQuery que oculta la segunda columna:

$('td:nth-child(2)').hide();

Si su tabla tiene encabezado (th), use esto:

$('td:nth-child(2),th:nth-child(2)').hide();

Source: Ocultar una columna de tabla con una sola línea de código jQuery

JsFiddle para probar el código: http://jsfiddle.net/mgMem/1/


Si quieres ver un buen caso de uso, echa un vistazo a mi entrada de blog:

Ocultar una columna de tabla y colorear filas en función del valor con jQuery .

 229
Author: Leniel Maccaferri,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-03-28 03:39:36

Puedes usar colgroups:

<table>
    <colgroup>
       <col class="visible_class"/>
       <col class="visible_class"/>
       <col class="invisible_class"/>  
    </colgroup>
    <thead>
        <tr><th class="col1">Header 1</th><th class="col2">Header 2</th><th class="col3">Header 3</th></tr>
    </thead>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
    <tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
</table>

Su script entonces podría cambiar solo la clase desire <col>.

 11
Author: Luis Melgratti,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-18 21:52:20

Lo siguiente debería hacerlo:

$("input[type='checkbox']").click(function() {
    var index = $(this).attr('name').substr(2);
    $('table tr').each(function() { 
        $('td:eq(' + index + ')',this).toggle();
    });
});

Este es un código no probado, pero el principio es que elija la celda de la tabla en cada fila que corresponda al índice elegido extraído del nombre de la casilla de verificación. Por supuesto, podría limitar los selectores con una clase o un ID.

 9
Author: Eran Galperin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-18 22:03:00

Y, por supuesto, la única forma de CSS para los navegadores que admiten nth-child:

table td:nth-child(2) { display: none; }

Esto es para IE9 y posteriores.

Para su caso de uso, necesitaría varias clases para ocultar las columnas:

.hideCol1 td:nth-child(1) { display: none;}
.hideCol2 td:nth-child(2) { display: none;}

Ect...

 3
Author: ProblemsOfSumit,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-10-31 08:40:10

Aquí hay una respuesta un poco más completa que proporciona cierta interacción del usuario por columna. Si esta va a ser una experiencia dinámica, debe haber un interruptor en el que se pueda hacer clic en cada columna que indique la capacidad de ocultar la columna y, a continuación, una forma de restaurar las columnas ocultas anteriormente.

Eso se vería algo como esto en JavaScript:

$('.hide-column').click(function(e){
  var $btn = $(this);
  var $cell = $btn.closest('th,td')
  var $table = $btn.closest('table')

  // get cell location - https://stackoverflow.com/a/4999018/1366033
  var cellIndex = $cell[0].cellIndex + 1;

  $table.find(".show-column-footer").show()
  $table.find("tbody tr, thead tr")
        .children(":nth-child("+cellIndex+")")
        .hide()


})

$(".show-column-footer").click(function(e) {
    var $table = $(this).closest('table')
    $table.find(".show-column-footer").hide()
    $table.find("th, td").show()

})

Para soportar esto, agregaremos algo de marcado a la tabla. En cada encabezado de columna, podemos agregar algo como esto para proporcionar un indicador visual de algo clickable

<button class="pull-right btn btn-default btn-condensed hide-column" 
            data-toggle="tooltip" data-placement="bottom" title="Hide Column">
    <i class="fa fa-eye-slash"></i>  
</button>

Permitiremos al usuario restaurar columnas a través de un enlace en el pie de tabla. Si no es persistente de forma predeterminada, entonces activarlo dinámicamente en el encabezado podría empujarse alrededor de la tabla, pero realmente puede ponerlo en cualquier lugar que desee:

<tfoot class="show-column-footer">
   <tr>
    <th colspan="4"><a class="show-column" href="#">Some columns hidden - click to show all</a></th>
  </tr>
</tfoot>

Esa es la funcionalidad básica. Aquí hay una demostración a continuación con un par de cosas más desarrolladas. También puede agregar una descripción al botón para ayudar a aclarar su propósito, estilo del botón un poco más orgánicamente a un encabezado de tabla, y contraer el ancho de la columna para agregar algunas animaciones CSS (algo torcidas) para hacer la transición un poco menos nerviosa.

Demostración Screengrab

Demostración de trabajo en jsFiddle & Stack Snippets:

$(function () {
  $('.hide-column').click(function(e){
    var $btn = $(this);
    var $cell = $btn.closest('th,td')
    var $table = $btn.closest('table')

    // get cell location - https://stackoverflow.com/a/4999018/1366033
    var cellIndex = $cell[0].cellIndex + 1;

    $table.find(".show-column-footer").show()
    $table.find("tbody tr, thead tr")
      .children(":nth-child("+cellIndex+")")
      .addClass('hide-col'); //.hide()
  })

  $(".show-column-footer").click(function(e) {
    var $table = $(this).closest('table')
    $table.find(".show-column-footer").hide()
    $table.find("th, td")
      .removeClass('hide-col'); //.show()

  })
  
  $('[data-toggle="tooltip"]').tooltip({trigger: 'hover'})

})
body {
  padding: 15px;
}
.table-hideable td,
.table-hideable th {
  width: auto;
  transition: width .5s, margin .5s;
}
.btn-condensed.btn-condensed {
  padding: 0 5px;
  box-shadow: none;
}

/* use class to have a little animation */
.hide-col {
    width: 0px !important;
    height: 0px !important;
    display: block !important;
    overflow: hidden !important;
    margin: 0 !important;
    padding: 0 !important;
    border: none !important;
}
<link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.3.7/css/bootstrap.css">
<link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/bootswatch/3.3.7/paper/bootstrap.min.css">
<link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.css">
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.3.7/js/bootstrap.min.js"></script>
    
  


<table class="table table-condensed table-hover table-bordered table-striped table-hideable">

  <thead>
    <tr>
      <th>
        Controller
        <button class="pull-right btn btn-default btn-condensed hide-column" 
                data-toggle="tooltip" data-placement="bottom" title="Hide Column">
          <i class="fa fa-eye-slash"></i>  
        </button>
      </th>
      <th>
        Action
        <button class="pull-right btn btn-default btn-condensed hide-column" 
                data-toggle="tooltip" data-placement="bottom" title="Hide Column">
          <i class="fa fa-eye-slash"></i>  
        </button>
      </th>
      <th>
        Type
        <button class="pull-right btn btn-default btn-condensed hide-column" 
                data-toggle="tooltip" data-placement="bottom" title="Hide Column">
          <i class="fa fa-eye-slash"></i>  
        </button>
      </th>
      <th>
        Attributes
        <button class="pull-right btn btn-default btn-condensed hide-column" 
                data-toggle="tooltip" data-placement="bottom" title="Hide Column">
          <i class="fa fa-eye-slash"></i>  
        </button>
      </th>
  </thead>
  <tbody>

    <tr>
      <td>Home</td>
      <td>Index</td>
      <td>ActionResult</td>
      <td>Authorize</td>
    </tr>

    <tr>
      <td>Client</td>
      <td>Index</td>
      <td>ActionResult</td>
      <td>Authorize</td>
    </tr>

    <tr>
      <td>Client</td>
      <td>Edit</td>
      <td>ActionResult</td>
      <td>Authorize</td>
    </tr>

  </tbody>
  <tfoot class="show-column-footer">
    <tr>
      <th colspan="4"><a class="show-column" href="#">Some columns hidden - click to show all</a></th>
    </tr>
  </tfoot>
</table>
 3
Author: KyleMit,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-01-23 20:48:38

Lo siguiente se basa en el código de Eran, con algunos cambios menores. Probado y parece funcionar bien en Firefox 3, IE7.

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" 
                "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<script src="http://code.jquery.com/jquery-latest.js"></script>
</head>
<script>
$(document).ready(function() {
    $('input[type="checkbox"]').click(function() {
        var index = $(this).attr('name').substr(3);
        index--;
        $('table tr').each(function() { 
            $('td:eq(' + index + ')',this).toggle();
        });
        $('th.' + $(this).attr('name')).toggle();
    });
});
</script>
<body>
<table>
<thead>
    <tr>
        <th class="col1">Header 1</th>
        <th class="col2">Header 2</th>
        <th class="col3">Header 3</th>
    </tr>
</thead>
<tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
<tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
<tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
<tr><td>Column1</td><td>Column2</td><td>Column3</td></tr>
</table>

<form>
    <input type="checkbox" name="col1" checked="checked" /> Hide/Show Column 1 <br />
    <input type="checkbox" name="col2" checked="checked" /> Hide/Show Column 2 <br />
    <input type="checkbox" name="col3" checked="checked" /> Hide/Show Column 3 <br />
</form>
</body>
</html>
 1
Author: Paolo Bergantino,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-18 22:15:35
<p><input type="checkbox" name="ch1" checked="checked" /> First Name</p>
.... 
<td class="ch1">...</td>

 <script>
       $(document).ready(function() {
            $('#demo').multiselect();
        });


        $("input:checkbox:not(:checked)").each(function() {
    var column = "table ." + $(this).attr("name");
    $(column).hide();
});

$("input:checkbox").click(function(){
    var column = "table ." + $(this).attr("name");
    $(column).toggle();
});
 </script>
 1
Author: lahbib,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-06-02 08:08:16

Sin clase? Puedes usar la etiqueta entonces:

var tds = document.getElementsByTagName('TD'),i;
for (i in tds) {
  tds[i].style.display = 'none';
}

Y para mostrarles el uso:

...style.display = 'table-cell';            
 0
Author: Gustavo Ruiz,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-08-13 16:32:44