una tabla filtrar filas dinamico bidimensional array javascript jquery html css cfml

javascript - tabla - Envolver listas en columnas



filtrar tabla html jquery (13)

Estoy usando ColdFusion para llenar una plantilla que incluye listas HTML ( <ul> ''s).

La mayoría de estos no son tan largos, pero algunos tienen longitudes ridículamente largas y realmente podrían estar en 2-3 columnas.

¿Hay alguna forma de HTML, ColdFusion o quizás JavaScript (tengo jQuery disponible) para hacerlo fácilmente? No vale la pena una solución pesada demasiado complicada para ahorrar algo de desplazamiento.


Para mostrar la lista en múltiples etiquetas agrupadas, puede hacer un bucle de esta manera.

<cfset list="1,2,3,4,5,6,7,8,9,10,11,12,13,14"> <cfset numberOfColumns = "3"> <cfoutput> <cfloop from="1" to="#numberOfColumns#" index="col"> <ul> <cfloop from="#col#" to="#listLen(list)#" index="i" step="#numberOfColumns#"> <li>#listGetAt(list,i)#</li> </cfloop> </ul> </cfloop> </cfoutput>


Así que desenterré este artículo de A List Apart Swag de CSS: listas de múltiples columnas . Terminé usando la primera solución, no es la mejor, pero las otras requieren ya sea el uso de HTML complejo que no se puede generar dinámicamente, o la creación de muchas clases personalizadas, lo que podría hacerse, pero requeriría un montón de estilo en línea y posiblemente una gran página.

Sin embargo, otras soluciones siguen siendo bienvenidas.


He hecho esto con jQuery: es multiplataforma y tiene un código mínimo.

Seleccione UL, clónelo e insértelo después de la UL anterior. Algo como:

$("ul#listname").clone().attr("id","listname2").after()

Esto insertará una copia de tu lista después de la anterior. Si la lista original tiene un estilo con un flotador: a la izquierda, deben aparecer uno al lado del otro.

Luego puede eliminar los elementos pares de la lista de la izquierda y los elementos impares de la lista de la derecha.

$("ul#listname li:even").remove(); $("ul#listname2 li:odd").remove();

Ahora tiene una lista de dos columnas de izquierda a derecha.

Para hacer más columnas, querrá usar .slice(begin,end) y / o el selector :nth-child . es decir, para 21 LI, podría hacer un " .slice(8,14) para crear un nuevo UL insertado después de su UL original, luego seleccionar el UL original y eliminar el li seleccionado con ul :gt(8) .

Prueba el libro Bibeault / Katz en jQuery es un gran recurso.


Usando una operación de módulo, puede dividir rápidamente su lista en múltiples listas insertando una </ul><ul> durante su ciclo.

<cfset numberOfColumns = 3 /> <cfset numberOfEntries = 34 /> <ul style="float:left;"> <cfloop from="1" to="#numberOfEntries#" index="i"> <li>#i#</li> <cfif NOT i MOD ceiling(numberOfEntries / numberOfColumns)> </ul> <ul style="float:left;"> </cfif> </cfloop> </ul>

Utilice ceiling() lugar de round() para asegurarse de que no tiene valores adicionales al final de la lista y que la última columna es más corta.


Aquí hay otra solución que permite listas de columnas en el siguiente estilo:

1. 4. 7. 10. 2. 5. 8. 11. 3. 6. 9. 12.

(pero es javascript puro, y requiere jQuery, sin recuperación)

A continuación, se incluye un código que modifica el prototipo de matriz para proporcionar una nueva función llamada "fragmento" que divide una matriz determinada en fragmentos de un tamaño determinado. Lo siguiente es una función llamada ''buildColumns'' que toma una cadena de selector UL y un número usado para designar cuántas filas pueden contener sus columnas. ( Aquí hay un JSFiddle que funciona )

$(document).ready(function(){ Array.prototype.chunk = function(chunk_size){ var array = this, new_array = [], chunk_size = chunk_size, i, length; for(i = 0, length = array.length; i < length; i += chunk_size){ new_array.push(array.slice(i, i + chunk_size)); } return new_array; } function buildColumns(list, row_limit) { var list_items = $(list).find(''li'').map(function(){return this;}).get(), row_limit = row_limit, columnized_list_items = list_items.chunk(row_limit); $(columnized_list_items).each(function(i){ if (i != 0){ var item_width = $(this).outerWidth(), item_height = $(this).outerHeight(), top_margin = -((item_height * row_limit) + (parseInt($(this).css(''margin-top'')) * row_limit)), left_margin = (item_width * i) + (parseInt($(this).css(''margin-left'')) * (i + 1)); $(this[0]).css(''margin-top'', top_margin); $(this).css(''margin-left'', left_margin); } }); } buildColumns(''ul#some_list'', 5); });


El siguiente código JavaScript funciona solo en Spidermonkey y Rhino, y opera en nodos E4X; es decir, esto es útil solo para el lado del servidor JavaScript, pero podría darle a alguien un punto de partida para hacer una versión de jQuery. (Ha sido muy útil para mí en el lado del servidor, pero no lo he necesitado lo suficiente en el cliente como para construirlo realmente).

function columns(x,num) { num || (num = 2); x.normalize(); var cols, i, j, col, used, left, len, islist; used = left = 0; cols = <div class={''columns cols''+num}></div>; if((left = x.length())==1) left = x.children().length(); else islist = true; for(i=0; i<num; i++) { len = Math.ceil(left/(num-i)); col = islist ? new XMLList : <{x.name()}></{x.name()}>; if(!islist && x[''@class''].toString()) col[''@class''] = x[''@class'']; for(j=used; j<len+used; j++) islist ? (col += x[j].copy()) : (col.appendChild(x.child(j).copy())); used += len; left -= len; cols.appendChild(<div class={''column''+(i==(num-1) ? ''collast'' : '''')}>{col}</div>); } return cols; }

Lo llama columns(listNode,2) para dos columnas, y da vuelta:

<ul class="foo"> <li>a</li> <li>b</li> <li>c</li> </ul>

dentro:

<div class="columns cols2"> <div class="column"> <ul class="foo"> <li>a</li> <li>b</li> </ul> </div> <div class="column collast"> <ul class="foo"> <li>c</li> </ul> </div> </div>

Está destinado a ser utilizado con CSS de esta manera:

div.columns { overflow: hidden; _zoom: 1; } div.columns div.column { float: left; } div.cols2 div.column { width: 47.2%; padding: 0 5% 0 0; } div.cols3 div.column { width: 29.8%; padding: 0 5% 0 0; } div.cols4 div.column { width: 21.1%; padding: 0 5% 0 0; } div.cols5 div.column { width: 15.9%; padding: 0 5% 0 0; } div.columns div.collast { padding: 0; }


Como tuve el mismo problema y no pude encontrar nada "limpio", pensé que había publicado mi solución. En este ejemplo, uso un ciclo while invertido para poder usar splice lugar de slice . La ventaja ahora es que empalme () solo necesita un índice y un rango donde slice () necesita un índice y el total. Este último tiende a ser difícil mientras se repite.

La desventaja es que necesito revertir la pila al agregar.

Ejemplo:

cols = 4; liCount = 35

para bucle con slice = [0, 9]; [9, 18]; [18, 27]; [27, 35]

invertido mientras que con splice = [27, 8]; [18, 9]; [9, 9]; [0, 9]

Código:

// @param (list): a jquery ul object // @param (cols): amount of requested columns function multiColumn (list, cols) { var children = list.children(), target = list.parent(), liCount = children.length, newUl = $("<ul />").addClass(list.prop("class")), newItems, avg = Math.floor(liCount / cols), rest = liCount % cols, take, stack = []; while (cols--) { take = rest > cols ? (avg + 1) : avg; liCount -= take; newItems = children.splice(liCount, take); stack.push(newUl.clone().append(newItems)); } target.append(stack.reverse()); list.remove(); }


Puede intentar esto para convertir en cols.

CSS:

ul.col { width:50%; float:left; } div.clr { clear:both; }

Parte Html:

<ul class="col"> <li>Number 1</li> <li>Number 2</li> <li>Number 19</li> <li>Number 20</li> </ul> <ul class="col"> <li>Number 21</li> <li>Number 22</li> <li>Number 39</li> <li>Number 40</li> </ul>


Lo que la mayoría de la gente está olvidando es que cuando se flotan elementos <li/> , todos los elementos tienen que tener la misma altura o las columnas comienzan a perderse.

Como está utilizando un lenguaje del lado del servidor, mi recomendación sería usar CF para dividir la lista en 3 arrays. Entonces puedes usar un ul externo para envolver las 3 ul internas así:

<cfset thelist = "1,2,3,4,5,6,7,8,9,10,11,12,13"> <cfset container = []> <cfset container[1] = []> <cfset container[2] = []> <cfset container[3] = []> <cfloop list="#thelist#" index="i"> <cfif i mod 3 eq 0> <cfset arrayappend(container[3], i)> <cfelseif i mod 2 eq 0> <cfset arrayappend(container[2], i)> <cfelse> <cfset arrayappend(container[1], i)> </cfif> </cfloop> <style type="text/css"> ul li { float: left; } ul li ul li { clear: left; } </style> <cfoutput> <ul> <cfloop from="1" to="3" index="a"> <li> <ul> <cfloop array="#container[a]#" index="i"> <li>#i#</li> </cfloop> </ul> </li> </cfloop> </ul> </cfoutput>


Flexbox se puede usar para envolver elementos en direcciones de fila y columna.

La idea principal es establecer la flex-direction en el contenedor a una row o column .

NB: Hoy en día , el soporte de navegador es bastante bueno.

VIOLÍN

(Marcado de muestra tomado de este viejo artículo de ''lista aparte'' )

ol { display: flex; flex-flow: column wrap; /* flex-direction: column */ height: 100px; /* need to specify height :-( */ } ol ~ ol { flex-flow: row wrap; /* flex-direction: row */ max-height: auto; /* override max-height of the column direction */ } li { width: 150px; } a { display: inline-block; padding-right: 35px; }

<p>items in column direction</p> <ol> <li><a href="#">Aloe</a> </li> <li><a href="#">Bergamot</a> </li> <li><a href="#">Calendula</a> </li> <li><a href="#">Damiana</a> </li> <li><a href="#">Elderflower</a> </li> <li><a href="#">Feverfew</a> </li> <li><a href="#">Ginger</a> </li> <li><a href="#">Hops</a> </li> <li><a href="#">Iris</a> </li> <li><a href="#">Juniper</a> </li> <li><a href="#">Kava kava</a> </li> <li><a href="#">Lavender</a> </li> <li><a href="#">Marjoram</a> </li> <li><a href="#">Nutmeg</a> </li> <li><a href="#">Oregano</a> </li> <li><a href="#">Pennyroyal</a> </li> </ol> <hr/> <p>items in row direction</p> <ol> <li><a href="#">Aloe</a> </li> <li><a href="#">Bergamot</a> </li> <li><a href="#">Calendula</a> </li> <li><a href="#">Damiana</a> </li> <li><a href="#">Elderflower</a> </li> <li><a href="#">Feverfew</a> </li> <li><a href="#">Ginger</a> </li> <li><a href="#">Hops</a> </li> <li><a href="#">Iris</a> </li> <li><a href="#">Juniper</a> </li> <li><a href="#">Kava kava</a> </li> <li><a href="#">Lavender</a> </li> <li><a href="#">Marjoram</a> </li> <li><a href="#">Nutmeg</a> </li> <li><a href="#">Oregano</a> </li> <li><a href="#">Pennyroyal</a> </li> </ol>


No hay una forma pura de CSS / HTML para lograr esto, hasta donde yo sé. Su mejor opción sería hacerlo en el procesamiento previo (si la longitud de la lista es> 150, dividida en 3 columnas, esle si es> 70, dividida en 2 columnas, sino 1).

La otra opción, usar JavaScript (no estoy familiarizado con la biblioteca jQuery específicamente) sería iterar a través de listas, probablemente porque una cierta clase de ellas es cierta, contar el número de hijos, y si es un número lo suficientemente alto, dinámicamente crea una nueva lista después de la primera, transfiere una cantidad de elementos de la lista a la nueva lista. En cuanto a la implementación de las columnas, probablemente podría flotarlas a la izquierda, seguidas por un elemento que tenía el estilo clear: left o clear: both .

.column { float: left; width: 50%; } .clear { clear: both; }

<ul class="column"> <li>Item 1</li> <li>Item 2</li> <!-- ... --> <li>Item 49</li> <li>Item 50</li> </ul> <ul class="column"> <li>Item 51</li> <li>Item 52</li> <!-- ... --> <li>Item 99</li> <li>Item 100</li> </ul> <div class="clear">


Si la compatibilidad con Safari y Firefox es lo suficientemente buena para ti, existe una solución CSS:

ul { -webkit-column-count: 3; -moz-column-count: 3; column-count: 3; -webkit-column-gap: 2em; -moz-column-gap: 2em; column-gap: 2em; }

No estoy seguro acerca de Opera.


Aquí hay una variación del ejemplo de Thumbkin (usando Jquery):

var $cat_list = $(''ul#catList''); // UL with all list items. var $cat_flow = $(''div#catFlow''); // Target div. var $cat_list_clone = $cat_list.clone(); // Clone the list. $(''li:odd'', $cat_list).remove(); // Remove odd list items. $(''li:even'', $cat_list_clone).remove(); // Remove even list items. $cat_flow.append($cat_list_clone); // Append the duplicate to the target div.

¡Gracias, Thumbkin!