Archivo para junio de 2012

Implicaciones

Ser creyente sólo implica credulidad, falta de espíritu analítico, incapacidad para ver la propia contradicción y bastante cobardía.

Inspirado en una respuesta de @teleoperador.

Libertad

La libertad es el derecho a decirle a la gente lo que no quieren escuchar.

George Orwell (1903 – 1950), escritor y periodista británico.

Lógica

Se para el ascensor y dentro está el profesor de lógica. Preguntamos:
—¿Sube o baja?
—Sí.

@INF_ENFURECIDO

Fe

La fe sólo es miedo disfrazado de virtud.

Pat Condell (1949), comediante inglés, escritor y personalidad de Internet, en un vídeo explicando por qué la religión no merece respeto.

Casualidad

Todo imbécil execrable, que no tiene en el mundo nada de que pueda enorgullecerse, se refugia en este último recurso, de vanagloriarse de la nación a que pertenece por casualidad.

Arthur Schopenhauer (1788 – 1860), filósofo alemán.

Función en Javascript para filtrar filas de una tabla

Como en la entrada anterior de Javascrip para crear solapas, para filtrar las filas de una tabla también existen multitud de ejemplos en la Web, incluidos plug-ins de jQuery.

Pero como a mi me gusta experimentar para aprender, aquí está mi versión del filtrado de filas de una tabla. De momento no es plug-in de jQuery pero, como la vez anterior, no creo que sea demasiado difícil adaptarlo. Y, por supuesto que tiene sus fallos, pero se irán subsanando con el tiempo.

function tablefilter(table_selector, input_selector, search_level, colspan) {
	var table = $(table_selector);
	if(table.length == 0)
		return;

	var input = $(input_selector);
	if(input.length == 0)
		return;

	if(search_level == "undefined" || search_level < 1)
		search_level = 3;

	if(colspan == "undefined" || colspan < 0)
		colspan = 2;

	$(input).val("Buscar…");

	$(input).focus(function() {
		if($(this).val() == "Buscar…") {
			$(this).val("");
		}
		$(this).select();
	});

	$(input).blur(function() {
		if($(this).val() == "") {
			$(this).val("Buscar…");
		}
	});

	$(input).keyup(function() {
		if($(this).val().length >= search_level) {
			// Ocultamos las filas que no contienen el contenido del edit.
			$(table).find("tbody tr").not(":contains(\"" + $(this).val() + "\")").hide();
			
			// Si no hay resultados, lo indicamos.
			if($(table).find("tbody tr:visible").length == 0) {
				$(table).find("tbody:first").append('<tr id="noresults" class="aligncenter"><td colspan="' + colspan + '">Lo siento pero no hay resultados para la búsqueda indicada.</td></tr>');
			}
		} else {
			// Borramos la fila de que no hay resultados.
			$(table).find("tbody tr#noresults").remove();
			
			// Mostramos todas las filas.
			$(table).find("tbody tr").show();
		}
	});
}

Para hacerlo funcionar basta con llamar a la función con dos, tres o cuatro parámetros (a elegir; si no se pasan se usan los predeterminados). El primer parámetro es el selector de la tabla a aplicar; el segundo es el input que se usará para el filtro; el tercero es el número de caracteres mínimos para comenzar la búsqueda (si no se especifica se usan tres); y el cuarto es el número de columnas que se debe extender la fila de información. Un ejemplo de llamada sería:

$(document).ready(function() {
  tablefilter("table#mi_tabla", "table thead tr input#filtro", 2, 3);
});

Internamente esta función usa el método contains() de jQuery para buscar. Este método distingue entre mayúsculas y minúsculas, así que, para hacer mejores búsquedas, se puede indicar que este método no distinga de la siguiente forma:

jQuery.expr[':'].contains = function(a, i, m) { 
  return jQuery(a).text().toUpperCase().indexOf(m[3].toUpperCase()) >= 0; 
};

En caso de que no funcione correctamente, se debe añadir exactamente lo mismo otra vez pero cambiando “.contains =” por “.Contains =“.

Y, cómo no, podéis ver un ejemplo del funcionamiento de la misma así como descargarlo.

Leyes e ideas

Las leyes deben defender a las personas, su integridad, sus posesiones, etc., pero las ideas, los pensamientos, los conceptos deben ser sometidos a la crítica sin correr el peligro de ser castigados; cada cual es libre de creer o no creer, y de cuestionar, rebatir, parodiar o “blasfemar” sin más límites que la integridad de las personas.

El mejor resumen que he visto de por qué hay que defender la crítica a las religiones —y a todas las ideas en general—. Comentario hecho por Makili en la noticia de Menéame sobre que Europa Laica pide la eliminación de la blasfemia como delito y felicita a Krahe por su absolución.

Persona media

Piensa en cómo de estúpida es una persona media. Después date cuenta que la mitad de las personas son aún más estúpidas.

George Carlin (1937 – 2008), cómico, actor y figura de la contracultura.

Principio de Hanlon

Nunca le atribuyas a la maldad lo que puede ser explicado por la estupidez.

Aunque está atribuida a Hanlon, no existe tal personaje y hay varios autores que la han mencionado, cosa que no le quita veracidad.

Por aquí ya la había puesto atribuyéndola, erróneamente, a Napoleón Bonaparte.

Función en Javascript para crear solapas (tabs)

Existen multitud de snippets y plug-ins de jQuery para hacer solapas con diferentes partes de una misma página, pero ninguno de ellos con las características que he implementado en esta función (que —todavía— no es un plug-in de jQuery). La principal característica que quería conseguir era la simplicidad.

La mayoría de estos plug-ins o funciones requieren que se haga un poco de marcado en HTML para delimitar tanto el conjunto de solapas como cada una de ellas, con lo que, al menos, habrá que marcar un <div> general y un <div> por cada solapa.

Con esta función lo que se pretende, como he comentado antes, es que ese marcado adicional sea innecesario usando sólo lo que ya existe dentro de la página para crear las solapas.

Es por esto que esta función lo que hace es, dentro de una caja (o del cuerpo completo del HTML), convertir en solapa todo el contenido que hay entre diferentes encabezados del mismo nivel (<h1>..<h6>), es decir, si existe una página bien formada con sus correspondientes encabezados, mediante esta función es trivial mostrarla como solapas.

El código de la función —y, repito, no es un plug-in para jQuery pero no sería demasiado difícil adaptarla— es el siguiente:

function Tabs(element, tabElement) {
    // Si no existe la caja de donde coger los elementos, nos salimos.
    if($(element).length == 0)
        return;

    // Si ya las hemos creado, no lo volvemos a hacer. De momento sólo se soportan unas tabs por página.
    if($(element).find("ul#tabs").length > 0)
        return;

    // Creamos una lista con los elementos de las solapas (serán los botones).
    var tabList = $("<ul>", { id: "tabs" });

    // Cogemos lo que hay entre cada 'tabElement' y lo metemos en un div
    var counter = 1;
    $(element).find(tabElement).each(function() {

        // Creamos una solapa para cada elemento y asignamos el evento "click".
        $(tabList).append($("<li>", { text: $(this).html(), id: "tab_" + counter }).click(function() {
            // Cuando hacemos click en la solapa, quitamos la selección.
            $(element).find("ul#tabs li").removeClass("selected");
            $(this).addClass("selected");
            var id = $(this).attr("id").substring(4);   // de "tab_1" nos quedamos con "1".
            $(element).find("div.tab_content").removeClass("selected");
            $(element).find("div.tab_content#tab_content_" + id).addClass("selected");

            // Reemplazamos la URL para que se refleje el cambio y, si se recarga la página, se recargue en el sitio correcto.
            var newurl = window.location.pathname;
            newurl = newurl.substring(newurl.indexOf("#") + 1) + "#tab_" + id;
            window.location.replace(newurl);

            // Volvemos a la parte de arriba de la página para que no queden ocultas las solapas por culpa de Drupal y su barra de administrador.
            // Otra opción podría ser volver un poco, en lugar de al principio. Por ejemplo: $(document).scrollTop($(document).scrollTop() - 10);
            $(document).scrollTop(0);
        }));

        // Metemos lo que hay entre los 'tabElement' en un div.
        $(this).nextUntil(tabElement).wrapAll("<div class='tab_content' id='tab_content_" + counter + "'></div>");

        // Borramos el elemento.
        $(this).remove();

        // Estos divs se ocultan con CSS.
        counter++;
    });

    // Añadimos la lista al div principal (pasado como parámetro).
    $(element).prepend(tabList);

    // Obtenemos el fragment (o hash) de la URL.
    var hash = window.location.hash;

    // Obtenemos el número de tab que sabemos está detrás de "_".
    hash = hash.substring(hash.indexOf("_") + 1);

    // Mostramos la primera solapa con el primer contenido (div) si no hay fragment. Si hay fragment
    // mostramos el que toca según el mismo (el fragment es #tab_x donde x es el número de tab [1..n]).
    if(hash != "" && $(tabList).find("li#tab_" + hash).length != 0) {
        $(tabList).find("li#tab_" + hash).addClass("selected");
        $(element).find("div.tab_content#tab_content_" + hash).addClass("selected");
    } else {
        $(tabList).find("li:first").addClass("selected");
        $(element).find("div.tab_content:first").addClass("selected");
    }
}

Como las solapas se crean con una lista (<ul>), se debe poner un poco de CSS para que se adapte, igual que se debe poner CSS para ocultar las solapas que no están visibles (en lugar de hacerlo con el propio Javascript modificando los atributos directamente, prefiero hacerlo con CSS añadiendo y/o quitando clases). El CSS básico (con un poco de estilo gráfico también) es el siguiente:

ul#tabs {
    margin: 10px 0;
    padding: 0;
    border-bottom: 1px solid silver;
    line-height: 29px;
}

ul#tabs li {
    display: inline-block;
    margin: 0 0 -1px -1px;
    padding: 0 10px;
    cursor: pointer;
    border: 1px solid silver;
    background: #DDDDDD;
    color: gray;
}

ul#tabs li.selected {
    background: white;
    color: #444444;
}

ul#tabs li:hover {
    background: #EEEEEE;
}

div.tab_content {
    display: none;
}

div.tab_content.selected {
    display: block;
}

Podéis ver un ejemplo de su funcionamiento y también podéis descargarlo para vuestro uso y disfrute (sin olvidarse de la licencia, claro).

Actualización 2012-06-07: Antonio me comenta que en IE9 (cómo no) no se ven bien las solapas. La lista que hará las solapas, al tener el CSS inline-block para que se muestren en una sola fila pero no se corten las solapas por la mitad, no se interpreta bien, por lo que salen en una lista normal. La solución sería que floten dichas solapas a la izquierda (anulando todo lo anterior del inline-block), más o menos así:

ul#tabs { overflow: auto; }
ul#tabs li { float: left; }

Diez razones en contra del matrimonio homosexual

  1. Ser homosexual no es natural. Los americanos españoles de verdad rechazan todo lo antinatural, como las gafas, el poliéster o el aire acondicionado.
  2. El matrimonio gay fomenta que la gente sea gay de la misma forma que estar con gente alta te hace más alto.
  3. Legalizar el matrimonio homosexual abrirá la puerta a todo tipo de comportamientos. La gente incluso podría casarse con sus mascotas porque un perro tiene personalidad jurídica y puede firmar un contrato de matrimonio.
  4. El matrimonio heterosexual ha existido durante mucho tiempo y no ha cambiado en absoluto: las mujeres todavía son propiedad, los negros no se pueden casar con los blancos y el divorcio todavía es ilegal.
  5. El matrimonio heterosexual tendrá menos sentido si se permite el matrimonio homosexual. El matrimonio de 55 horas sólo por diversión de Britney Spears sería destruido. Casarse por la iglesia porque te gusta el rito en lugar de porque eres creyente sería prohibido.
  6. El matrimonio heterosexual es válido porque produce hijos. A las parejas gays, a las parejas infértiles y la gente mayor no se les debería permitir casarse porque los orfanatos todavía no están llenos y el mundo necesita más niños.
  7. Obviamente, padres homosexuales criarán hijos homosexuales de la misma forma que padres heterosexuales crían hijos heterosexuales.
  8. El matrimonio gay no es compatible con la religión. En una teocracia como la nuestra los valores de una religión son impuestos en todo el país. Es por esto que sólo hay una religión en América España.
  9. Los niños nunca tendrán éxito sin una figura paterna y una figura materna en casa. Es por esto que nosotros, como sociedad, prohibimos expresamente que los padres solteros críen hijos.
  10. El matrimonio homosexual cambiará el fundamento de la sociedad; nunca podremos adaptarnos a las nuevas normas morales al igual que no nos hemos adaptado a los coches, a la economía del sector servicios o a vidas más largas.

A ver, espero que no haga falta decir que es humor, ¿verdad?

Por cierto, lo saqué de esta imagen que circula por Internet en inglés; y de ahí la traducción libre aunque adaptando las referencias de la sociedad americana estadounidense a la española. Y está claro que somos exactamente igual de intolerantes.

Conocer la fecha de instalación de Windows y Linux

¿Nunca os habéis preguntado cuándo fue la última vez que instalasteis el sistema operativo que estáis usando? Quizás para presumir que no hace falta reinstalar cuando va más lento, quizás para ver que «ya toca» reinstalar…

El caso es que si queréis saberlo, podéis ejecutar estos comandos en un terminal:

En Windows XP/Vista/7:

C:\Documents and settings\Administrador> wmic get os InstallDate
InstallDate
20120601140000.000000+060

O también con systeminfo (que proporciona información más legible):

C:\Documents and settings\Administrador> systeminfo | find “instalación”
Fecha de instalación original:          01/06/2012, 14:00:00

En Linux:

user@desktop:~:$ sudo tail /var/log/installer/syslog

Con lo que nos mostrará las últimas líneas del log de instalación y podremos ver la fecha del mismo. Otra opción es buscar el archivo más antiguo (suponiendo que no haya sido modificado posteriormente):

user@desktop:~:$ ls -lct /etc | tail -1 | awk ‘{print $6, $7, $8}’
jun 01 14:00

O también (ya sabéis que en Linux hay mil formas de hacer la misma operación) podéis mirar la fecha de creación de la partición donde está instalado el sistema (aunque también puede dar lugar a fallos debido a que podéis haber instalado sobre una versión antigua):

user@desktop:~:$ dumpe2fs -h /dev/sda2 | grep created
dumpe2fs 1.42 (29-Nov-2011)
Filesystem created:     Fri Jun 01 14:00:00 2012

Y, bueno, mis fechas de instalación —en el trabajo— son, la de Windows (en una máquina virtual ya que uso Linux) el 26 de febrero de 2010 y la de Linux el 11 de diciembre de 2009, aunque he de decir que ahora uso más un Linux recién instalado —del 27 de abril de este año— ya que lo estoy probando en un disco SSD.

En casa os aseguro que bastante más :grin: .