sexta-feira, 4 de março de 2011

Jquery Plugin: Simple Gallery - Galeria simples

Existem casos em que é difícil utilizar algumas daquelas maravilhosas galerias em Jquery, muitas vezes criadas por designers cheios de inspiração, que exalam interatividade e qualidade. Pode ocorrer também, de um cliente de um website do qual você é responsável, simplesmente não gostar destes tipos de galerias ou quem leiautou o site simplesmente criou a idéia de uma galeria "maluca" do qual o cliente adorou e não quer trocar por nada. Para estes casos eu desenvolvi um plugin de fácil adaptação que poderá lhe ajudar e salvar um tempo precioso de desenvolvimento.

Download e exemplos

Abaixo você pode baixar o plugin, juntamente com um exemplo de uso:

Agora ficou fácil

O Jquery Simple Gallery é um plugin que permite uma fácil adaptação para diferentes tipos de leaiautes de galerias, não dependendo de complexas estilizações, basta apenas dizer onde você quer que a ampliação apareça, definir os elementos da página que vão servir de botões de navegação e ainda opcionalmente, pode definir a visualização de miniaturas, para melhorar um pouco a interação do usuário com a galeria.

Chamando o plugin

$('#gallery').simpleGallery({
    'data' : 'pictures.php',
    'imagePrev' : '#prevButton',
    'imageNext' : '#nextButton'
});

Bastam três parâmetros para criar a galeria: data, imagePrev, imageNext

Marcação HTML

A única marcação que você precisará declarar em seu documento, serão os elementos que você utilizou como parâmetro:

<div id="imagePrev"></div>
<div id="gallery"></div>
<div id="imageNext"></div>

Só faltam as imagens

Agora a única peça que falta é conseguir uma lista com as imagens que você quer que apareçam em sua galeria, isto é feito por meio de um arquivo com um objeto JSON no seguinte formato:

{
    "images": [
        "caminho/da/imagem/01.jpg",
        "caminho/da/imagem/02.jpg"
  ...
    ],
    "thumbs": [
        "caminho/da/miniatura/01.jpg",
        "caminho/da/miniatura/02.jpg",
  ...
    ]
}

No arquivo disponível para download, você terá uma solução pronta criada em php para conseguir criar este objeto com facilidade.

Extendendo as possibilidades

Abaixo segue a lista de parâmetros disponíveis para este plugin.

  • String data:
    • Função: o arquivo responsável por criar o objeto JSON com a lista de imagens e thumbs da galeria;
    • Default: vazio
  • String/Bool counter:
    • Função: define um elemento para mostrar um contador de imagens. Ex: 5 / 10
    • Default: false (não será mostrado)
  • String imagePath:
    • Função: caminho onde encontram-se as imagens. O valor deste parâmetro será passado para o arquivo definido no parâmetro data via método GET.
    • Default: images/
  • String imagePrev:
    • Função: Elemento utilizado para retornar a uma imagem anterior.
    • Default: vazio
  • String imageNext:
    • Função: Elemento utilizado para avançar para uma próxima imagem.
    • Default: vazio
  • String/Bool filmstrip:
    • Função: Defina o elemento da página onde deseja mostrar as miniaturas, deixe em branco para não mostrar.
    • Default: false (não será mostrado)
  • Integer frames:
    • Função: Define quantas miniaturas serão mostradas no elemento definido em filmstrip
    • Default: 6
  • String thumbPath:
    • Função: caminho onde encontram-se as miniaturas. O valor deste parâmetro será passado para o arquivo definido no parâmetro data via método GET.
    • Default: thumbs/
  • String thumbPrev:
    • Função: Elemento utilizado para retroceder nas miniaturas. Caso não seja definido, este elemento será criado automáticamente.
    • Default: #simple-gallery-filmstrip-prev


  • String thumbNext:
    • Função: Elemento utilizado para avançar nas miniaturas. Caso não seja definido, este elemento será criado automáticamente.
    • Default: #simple-gallery-filmstrip-next


  • String loadMessage:
    • Função: Defina uma mensagem ou gif padrão para ser mostrada enquanto uma imagem estiver sendo carregada.
    • Default: Carregando ...


Licença de uso

O plugin esta sobre a licença MIT de uso.

Finalizando

Mais um plugin para facilitar nossas vidas, existem ajustes a serem feitos para melhorar um pouco a interface do usuário, mas tenho certeza que da maneira que esta hoje, ele já pode ser utilizado em muitas situações e salvar um tempo precioso.

terça-feira, 22 de fevereiro de 2011

Plugin: Jquery Endless Page (Infinite scroll)

Um recurso muito utilizado na web 2.0 é permitir que o usuário ao clicar em um botão ou sempre que o scroll chegue ao fim de um conteúdo, possa ver mais resultados de uma busca, substituindo a paginação comum, este plugin permite trabalhar das duas formas.

Utilizando um gatilho

A chamada do plugin baseado em um gatilho é bem simples, basta informar:

  • O seletor utilizado para a chamada do plugin, que deverá ser a div onde o conteúdo será mostrado;
  • Um arquivo backend com a lógica para mostrar o conteúdo
  • O seletor do gatilho, que poderá ser: div/span/a, ou qualquer elemento onde o texto possa ser capturado com o método .text() do Jquery;
$('#Content').ep({
   'content'  : 'content.php',
   'trigger'  : '#More'
});

Exemplo de chamada do plugin utilizando um gatilho

Utilizando o scroll como gatilho

Por default, o plugin irá definir o gatilho como sendo o scroll, então se o parâmetro trigger for omitido na chamada do plugin, automáticamente o scroll será selecionado como gatilho.

$('#Content').ep({
   'content'  : 'content.php'
});

Para definir o scroll como o gatilho do plugin, basta omitir este parâmetro.

Outros parâmetros

Abaixo segue uma demonstração da utilização do plugin com todos os parâmetros disponíveis sendo declarados:

$('#Content').ep({
   'content'   : 'content.php',
   'trigger'   : '#More',
   'results'   : 10,
   'message'   : 'Loading...',
   'beforeLoad': function(){
      $('#Console').text('Carregando ...');
   },
   'onLoad'    : function(){
      $('#Console').text('');
   },
   'onEnd'     : function(){
      $('#Console').text('Fim dos resultados');
   }
});

Abaixo a função de cada parâmetro:

  • String content:
    • Função: o arquivo backend, com a lógica para a visualização dos resultados;
    • Default: não há
  • String trigger:
    • Função: O seletor do gatilho, que poderá ser: div/span/a, ou qualquer elemento onde o texto possa ser capturado com o método .text() do Jquery, para utilizar o scroll basta omitir este parâmetro;
    • Default: scroll
  • Integer results:
    • Função: o número de resultados que deverão ser mostrados por requisição;
    • Default: 1
  • String message:
    • Função: O texto alternativo que substituirá o texto original do trigger enquanto o conteúdo estiver sendo carregado;
    • Default: Carregando...
  • Function beforeLoad:
    • Função: uma função para ser executada antes do conteúdo ser carregado;
    • Default: void(0)
  • Function onLoad:
    • Função: uma função para ser executada após o conteúdo ser carregado;
    • Default: void(0)
  • Function onEnd:
    • Função: uma função para ser executada quando não houver mais conteúdo a ser carregado;
    • Default: void(0)

Exemplos de utilização

Abaixo seguem dois exemplos, o primeiro mostra como fazer para carregar mais conteúdo em uma página e o outro mostra como carregar mais imagens para uma galeria, se quiser baixar os dois de uma vez só, utilize o terceiro link.

A lógica por traz do plugin

Para finalizar, é preciso entender uma pequena característica do plugin, cada vez que ele é chamado, um contador (counter) tem seu valor adicionado com o valor definido no parâmetro results, tanto o valor da variável counter quanto o valor da variável results são passados pelo plugin via GET, para o arquivo backend. Para que o conteúdo seja carregado da maneira correta você precisará trabalhar a lógica em cima destas duas variáveis. Nos exemplos disponibilizados acima, você verá com detalhes como pode fazer isso.

Licença de uso

O plugin esta sobre a licença MIT de uso.

Finalizando

É isto, espero que tenham apreciado, dúvidas e sugestões fique livre para comentar.

Até uma próxima!

sexta-feira, 28 de janeiro de 2011

Macetes: Comparando data e hora em PHP utilizando MySQL

O PHP não é muito feliz quando o assunto é comparar data e hora, sempre que procuro boas alternativas para fazer isto no PHP, continuo ainda preferindo a versão do MySQL, que uso já há algum tempo. Por incrível que pareça ela ainda consegue ser mais limpa, rápida e acurada do que as soluções feitas somente em PHP.

Para fazer esta comparação em MySQL basta utilizar a função TIMEDIFF dentro de uma query SELECT:

SELECT TIMEDIFF('AAAA-MM-DD HH:MM:SS', 'AAAA-MM-DD HH:MM:SS')

Se o primeiro parâmetro for uma data menor que o segundo, então o valor retornado será negativo, o que pode ser bom para em casos que você tenha que descobrir se algo já passou de algum prazo estipulado.

No PHP você poderia trabalhar da seguinte forma:


$sql = mysql_query("SELECT TIMEDIFF('2011-01-28 09:00:00','2011-01-28 00:00:10') as dif");

$time = mysql_fetch_array($sql);

echo($time[dif]);

O resultado final será a diferença em horas, o que em muitos casos é o suficiente, agora se você precisa de outros formatos, terá que recorrer a outras funções.

Até a próxima!

quinta-feira, 27 de janeiro de 2011

Macetes: Javascript, substituindo todas as ocorrências dentro de uma string (Replace All)

Ao contrário do PHP, o JavaScript não possui funções que fazem o replace de várias ocorrências de uma substring dentro de uma string, como acontece nas funções muito conhecidas pelos desenvolvedores do elefante azul: preg_replace() e str_replace().

Você pode até procurar e encontrar na net, funções denominadas replaceAll() que fazem este trabalho para você no Java Script, mas nenhuma delas é nativa da linguagem e sim funções criadas por usuários.

Infelizmente, como ocorreu comigo, estas funções geralmente apresentam bugs, principalmente quando você precisa escapar caracteres como \ (contra barra) e " (aspas duplas), que comumente precisam deste tipo de tratamento quando estamos trabalhando com strings.

O único método nativo do Java Script para fazer substituição dentro de strings é o método replace(), ele por padrão substitui apenas o primeiro valor encontrado e é ele quem serve de base para aquelas funções customizadas citadas anteriormente. Para felicidade geral, este método esconde um pequeno segredinho, que faz ele mudar seu comportamento e substituir todas as ocorrências dentro de um string. Confira abaixo:

//Uma string qualquer
var str = 'Vou incomodar você com estas "aspas duplas"';

//A primeira aspas duplas encontrada ganhará uma contra barra grátis
str = str.replace(/\"/,'\\"');

//Resultado: Vou incomodar você com estas \"aspas duplas"
document.write(str);

Como dito, apenas a primeira aspas duplas ganhou a contra barra, agora vamos utilizar o modificador g para fazer um Global Match e substituir todas as " por \".

//Uma string qualquer
var str = 'Vou incomodar você com estas "aspas duplas"';

//Repare onde você deve colocar o modificador (destacado em azul)
str = str.replace(/\"/g,'\\"');

//Resultado: Vou incomodar você com estas \"aspas duplas\"
document.write(str);

Espero que este macete possa lhe ajudar como me ajudou, apesar do "lance" das aspas ser apenas um exemplo, ele pode causar vários problemas, principalmente quando você esta criando uma string para criar um objeto JSON e dentro desta string você precisa permitir que sejam passados valores com aspas duplas, se elas não forem devidamente escapadas antes de você concatenar seu valor na string JSON, com certeza o Java Script vai berrar.

Abraço!

quarta-feira, 26 de janeiro de 2011

Macetes - Regex no Notepad++ - Reescrevendo valores

Vamos explicar este macete com uma pequena historinha, se quiser pulá-la e ir direto ao ponto, clique aqui.

Digamos que seu chefe passou hoje por você, te achou meio ocioso e decidiu sacanear você um pouco. Trouxe então uma planilha do Excel com uma lista interminável de clientes e pediu que você excluísse do sistema da empresa, todos os clientes que estão marcados como "desativado" na planilha.

Você sacando a jogada do seu chefe, aceitou de boa e ainda exclamou: "Meu, isso vai levar a tarde inteira, senão um dia inteiro!". Seu chefe, vendo seu desespero apenas respondeu: "Então, boa sorte!"

Como você já havia lido o post: "Macetes - Regex no Notepad++ - Reescrevendo valores" no Programação de Resultado, você calmamente acessou a já conhecida planilha e sabiamente ordenou todos os registros pelo id do cliente, que felizmente é igual tanto na planilha quanto no sistema. Selecionou então a coluna e colou todos os ids no seu Notepad++.

Em seguida com grande familiaridade, deu um CTRL+F na janela do Notepad++ e abriu a janela de Localizar, selecionou Expressão regular no canto inferior esquerdo da janela e digitou a seguinte expressão no campo Localizar : ([0-9]+), conferiu então se a expressão funcionou corretamente clicando no botão Localizar próximo e constatou que tudo ocorre bem.

Na sequência, ainda na janela Localizar, clicou na aba Substituir, posicionou o cursor do mouse no campo Substituir por e então digitou: DELETE FROM clientes WHERE id = \1;. Por fim clicou no botão Substituir todos e o Notepad++ fez a mágica de criar uma query para cada número encontrado no arquivo, você apenas executou a query no banco de dados e "Voilà", todos os clientes desativados foram excluídos do sistema como seu chefe pediu.

Agora, de duas uma, ou você chega para o seu chefe 5 minutos depois de te passar esta tarefa e diz que esta pronto fazendo "mó média" e ele apesar de espantado percebe que você sabia que ele tava te sacaneando e então você se aproveitou para sacanear ele também, mostrando o quanto você é bom e que não pode ser enrolado com essas tarefas frívolas, portanto ele decide contra sacanear e te passa mais trabalho (que frase longa), ou você faz tudo em 5 minutos e enrola um dia inteiro para entregar e chega para ele dizendo: "Aquela tarefa, esta pronta!", ele te questiona "Ok! Deu muito trabalho?", você fazendo aquela cara de "Ufa!", diz: "Que nada chefe, precisando estamos aí!".

A decisão é sua.

Explicando o macete

No notepad++ digite entre parênteses, uma expressão regular qualquer, isto informa ao Notepad++ que você esta procurando um grupo de caracteres em particular, estando a expressão entre parênteses você consegue utilizar o valor encontrado na hora de substituí-lo por outro, é como se nós concatenássemos o valor encontrado ao novo valor que queremos escrever.

No exemplo nós utilizamos: ([0-9]+), para encontrar todos os números possíveis no arquivo, o valor encontrado para esta expressão, ficará armazenado pelo Notepad++ e você poderá acessá-los por meio de uma série de palavras reservadas: \1, \2, \3, \4, \5 ..., sendo que \1 representa o valor encontrado no primeiro grupo, \2 o valor encontrado para o segundo grupo encontrado e assim por diante.

Espero que tenham apreciado o post. Até a próxima.

quarta-feira, 19 de janeiro de 2011

Vídeo: Desconectar para conectar

Hoje pela manhã fui surpreendido por este vídeo, confesso que me arrepiei.
Se trata de um comercial de uma empresa telefônica que basicamente mostra a maneira como nos entretemos em nossos celulares "mil e uma utilidades" para ficar em contato com outras pessoas e acabamos esquecendo aqueles que estão a nossa volta.

Como o blog trata de tecnologia, não pude deixar de postar.

Confira o vídeo:



A contribuição é do meu amigo Marcos Minharo.

segunda-feira, 10 de janeiro de 2011

Tutorial: Paginação em ajax, utilizando a classe Paging e o plugin Jquery Table Sorter

Como sei que paginação em php é (quase)sempre um problema, resolvi criar uma classe para fazer esse trabalho por mim de uma maneira bem simples e escalável, é a classe Paging, que já foi apresentada anteriormente nos posts: Paginação simples e rápida em PHP utilizando a classe Paging e Tutorial: Utilizando a classe Paging para criar uma paginação simples e rápida.

Na versão em que ela se encontra, os únicos dados que conseguimos paginar são resultados tabelados, ou seja gerar um grid de dados com paginação, mas a idéia é futuramente poder paginar vários tipos de dados, como conteúdo html e imagens, porém, como falta-me tempo não consegui implementar métodos para isso, se você quiser contribuir fique a vontade. Deixando o papo de lado, vamos a solução.

Criando paginação utilizando ajax

Arquivos necessários

Para este tutorial iremos utilizar a biblioteca Jquery e o plugin Jquery Table Sorter. Ambos já estão inseridos no arquivo compactado disponível para download abaixo, juntamente com a classe Paging e os demais arquivos necessários para criar a paginação em ajax.

Entendendo os arquivos

/css

Neste diretório você irá encontrar duas folhas de estilos, uma utilizada simplesmente para estilizar o arquivo index.html e a outra é a folha de estilização padrão baixada juntamente com o plugin Jquery Table Sorter.

/img

Neste diretório são encontradas apenas imagens utilizadas no plugin Jquery Table Sorter.

/lib

Aqui você encontrará dois subdiretórios: /js e /php, neles você encontrará o a biblioteca Jquery e o plugin Jquery Table Sorter, além da classe de paginação Paging e a classe Connection, utilizada pela classe Paging para fazer uma conexão com um banco de dados. Caso você tenha dúvidas de como implementar esta conexão de uma olhada neste tutorial. Você não vai precisar mexer em nada nestes arquivos, a não ser que queira inserir novos métodos.

produtos.sql

Utilizamos este sql apenas para este exemplo, mas você pode facilmente configurar nossa solução para a tabela que você quiser.

paging.js

Este arquivo é quem faz o trabalho de criar as chamadas em ajax, para fazermos uma paginação sem recarga de página, a não ser que você queira implementar alguma nova funcionalidade, não é preciso mudar nada nele.

index.php

Neste documento encontramos a marcação necessária para apresentarmos os elementos básicos de nossos dados paginados:
  1. Uma div para procurarmos registros (search)
  2. Uma div que irá mostrar os registros encontrados (grid)
  3. Uma ou mais divs para mostrar os controles da paginação (controls)
  4. As chamadas a estilos e scripts necessários para fazer o "show" acontecer.
No arquivo que você for implementar esta solução, você não precisa nomear os ids/classes das divs exatamente como neste exemplo (grid, controls e search), fique livre para nomeá-los como achar melhor.

Criando paginação em ajax configurando apenas dois arquivos

grid.php

Este é um dos dois arquivos que você precisará alterar para fazer a mágica acontecer, são apenas 6 linhas que teremos que alterar (em negrito):

require_once('lib/php/paging.class.php');
$paging = new Paging();
$searchfor = isset($_GET['searchfor']) ? $_GET['searchfor'] : '';
$paging->table('produtos');
$paging->where('id = "'.$searchfor.'" OR nome LIKE "%'.$searchfor.'%" OR tipo LIKE "%'.$searchfor.'%"');
$paging->labels('ID,Nome,Tipo');
$paging->fields('id,nome,tipo');
$paging->cols_width('10,100,40');
$paging->rowsperpage(10);
$paging->page(isset($_GET['p']) ? $_GET['p'] : 1);

if($_GET['load'] == 'controls'){

$paging->show_controls();

}else{

$paging->show_table();

}
  1. require_once('lib/php/paging.class.php'); - altere para o diretório onde você irá armazenar as classes paging.class.php e connection.class.php
  2. $paging->table('produtos'); - informe o nome da tabela que contém os dados que deverão ser paginados
  3. $paging->where... - caso você opte por inserir a função search ao grid, defina aqui quais campos e condições para que os dados sejam mostrados, a sintaxe vai ser sempre similar a mostra neste exemplo, basicamente serão apenas os campos buscados que irão mudar.
  4. $paging->labels('ID,Nome,Tipo'); - Aqui serão definidos os cabeçalhos do grid
  5. $paging->fields('id,nome,tipo'); - Aqui você deve informar quais as colunas da tabela, que você deseja mostrar
  6. $paging->cols_width('10,100,40'); - Esta linha é opcional, mas caso você venha a ter problemas com os tamanhos (width) das colunas do grid, você pode ajustá-las aqui, basta colocar os tamanhos separados por vírgula para as respectivas colunas.
Você pode configurar ainda mais sua paginação, confira todos os métodos disponíveis para a classe acessando o post: Paginação simples e rápida em PHP utilizando a classe Paging.

param.js

Este é o segundo e último arquivo que você terá que modificar, não tem muito o que explicar nele, pois esta tudo devidamente comentado, de qualquer forma vamos mostrar aqui apenas para você ver como é fácil:
Configurando os controles da paginação
  1. var controlsdivclass = '.paging'; - Informe aqui em quais divs você deseja mostrar os controles da paginação, você pode ter os mesmos controles em diferentes divs;
  2. var controlsscript = 'grid.php'; - Informe aqui qual arquivo irá processar os registros e criar os controles;
  3. var controlsclass = 'tablesorter'; - Classe utilizada para estilizar os controles
Configurando o grid
  1. var griddivid = '#grid'; - Informe a div onde será mostrado o grid
  2. var gridscript = 'grid.php'; -Informe aqui qual arquivo irá processar os registros e criar o grid;
  3. var controlsclass = 'tablesorter'; - Classe utilizada para estilizar o grid
  4. var gridheaders = {}; - objeto utilizado para passar instruções ao plugin Jquery Table Sorter, parametrizando os cabeçalhos da tabela individualmente, algo do tipo: 0:{sorter:false}, 1:{sorter:false}...
Outros parâmetros
  1. var consolediv = '#console'; - Div utilizada para mostrar mensagens de status da execução
  2. var loadmsg = 'Carregando...aguarde'; - mensagem ou caminho para um gif animado para ser mostrado enquanto os dados estão sendo carregados
  3. var searchid = '#searching'; - Id do input (text) que será utilizado para fazer o search dentro do grid.
Configurando corretamente, você terá um resultado semelhante ao abaixo. Tente fazer isso para suas tabelas, você verá como ficará fácil implementar paginação no seu site ou sistema.


Resultado final da paginação com classe Paging + Ajax (Jquery e Jquery Table Sorter)

Se você é um usuário já experiente em Jquery, deve estar se perguntando porque eu não criei este grid como um plugin jquery, já que seria bem mais fácil de configurá-lo ao invés de utilizar um arquivo para configuração, a verdade é que eu nunca criei um plugin jquery, pois até então nunca tive a necessidade, a idéia é que eu transforme este grid em um plugin mais tarde, assim que eu tiver tempo para isso, se você já tem experiência no assunto, gostou da solução, tiver idéias ou quiser contribuir, fique a vontade, eu adoraria transformar isto em um plugin, principalmente em um gratuito, já que o plugin para criar grids com jQuery oficial (jqGrid) que existe hoje é uma solução paga.

É isso então, espero que tenham apreciado, deixem seus comentários, sugestões ou dúvidas que terei prazer em atendê-los. Até a próxima!