SASSPara finalizar esta série sobre o mjamado.com, falta falar sobre o que é, para mim, a tecnologia mais útil que aprendi no último ano: SASS, um superset da linguagem CSS, juntamente com Compass, uma biblioteca de mixins para usar com SASS (mixins é o termo convencionado para referir o que não são mais que pequenas funções).

Não vou alongar-me sobre todas as vantagens do SASS (estão aí os links, é dar uma voltinha), mas vou focar quatro pontos que me são caros.

Variáveis

Isto tem sido pedido à W3C inúmeras vezes, e que falta faz à especificação CSS. Uma das maiores dores de manutenção é precisamente mudar o esquema de cores, ou tamanhos das fontes; era óptimo poder definir-se este tipo de coisas numa variável. Ainda bem que o SASS suporta:

$baseColor: #349AFF;
$lightBaseColor: #4DA7FF;
$darkBaseColor: #1363B2;

body
{
  background-color: $baseColor;
  color: $darkBaseColor;
}

.highlight
{
  background-color: $lightBaseColor;
  color: $baseColor;
}

Expressões e funções com variáveis

O CSS3 trouxe a função calc(), que não serve exactamente a mesma coisa, mas veio colmatar outra lacuna há muito pedida por webdesigners, a capacidade de atribuir valores provenientes duma expressão. No entanto, a função calc() serve apenas para valores válidos (o CSS não tem variáveis, certo?) – não tem o uso que poderia ter como facilitadora de desenvolvimento; deixando de lado, claro, que o suporte é muito fraco (nem o Opera, nem o Safari suportam) e que coloca alguns problemas de performance no renderer dos browsers.

O uso das expressões e funções, no SASS, está intimamente ligado à capacidade de serem usadas variáveis. Um exemplo seria a manutenção de proporções ao nível do tamanho de letra (no exemplo abaixo, é usada a proporção áurea):

$baseFontSize: 12px;
$phi: 1.618;
$phi2: $phi*$phi;
$phi3: $phi2*$phi;

p, h6 { font-size: $baseFontSize; }
h5 { font-size: round($baseFontSize*$phi); }
h4 { font-size: round($baseFontSize*$phi2); }
h3 { font-size: round($baseFontSize*$phi3); }
h2 { font-size: round($baseFontSize*$phi2*$phi2); }
h1 { font-size: round($baseFontSize*$phi3*$phi2); }

Mixins

Mixins são funções definidas por nós, prontas a usar no estilo que nos aprover. Podendo aceitar parâmetros, as aplicações são ilimitadas. Por exemplo, vamos construir um gradiente cross-browser pronto a usar em vários sítios:

@mixin gradienteLinear($cor1, $cor2)
{
  /* Firefox 3.6+ */
  background: -moz-linear-gradient(top, $cor1, $cor2);
  /* Chrome, Safari 4+ */
  background: -webkit-gradient(
    linear, top, bottom, color-stop(0%, $cor1), color-stop(100%, $cor2)
  );
  /* Chrome 10+, Safari 5.1+ */
  background: -webkit-linear-gradient(top, $cor1, $cor2);
  /* Opera 11.10+ */
  background: -o-linear-gradient(top, $cor1, $cor2);
  /* Internet Explorer 10+ */
  background: -ms-linear-gradient(top, $cor1, $cor2);
  /* standard */
  background: linear-gradient(top, $cor1, $cor2);
  /* Internet Explorer 6+ */
  filter: progid:DXImageTransform.Microsoft.gradient(
    startColorstr='$cor1', endColorstr='$cor2', GradientType=0
  );
}

.btn
{
  @include gradienteLinear(#AAA, #CCC);
}

Na linha 1 defino o mixin; dentro, tenho todas as declarações necessárias. Depois, na linha 21, incluo esse mixin numa classe. A CSS resultante terá as declarações dentro da classe. Embora não reduza o tamanho do CSS resultante (o melhor que o tradutor fará será retirar comentários, espaçamentos e quebras de linha desnecessárias), reduz consideravelmente a complexidade de desenvolvimento.

Claro que este exemplo concreto foi propositado...

Compass

Como disse no início, o SASS tem um projecto intimamente ligado, o Compass, uma biblioteca de mixins – os autores definem-no como uma plataforma de desenvolvimento CSS, mas, embora tenha algumas ferramentas iniciais úteis (é possível começar-se a partir duma base Blueprint ou 960 Grid, por exemplo), é basicamente um repositório de mixins.

Uma voltinha pela referência oficial fará saltar à vista imensos mixins úteis para atalhar trabalho, sobretudo em áreas onde é preciso especificar os vários prefixos dos browsers. O exemplo acima poderia ser reescrito, usando Compass, da seguinte forma:

@import "compass/css3/images"

.btn
{
  @include background-image(linear-gradient(top, #AAA, #CCC));
}

Na primeira linha é importada a biblioteca do Compass que contém os mixins desejados, e, na classe, é só incluir o mixin concreto. Mais simples não podia ser.

De notar que este mixin em particular não inclui a declaração específica do Internet Explorer 9 e inferiores (via filter). Os criadores do Compass são defensores convictos que as especificidades do Internet Explorer devem ser tratadas por estilos condicionais, e visto que a declaração filter não é, nem de perto, nem de longe, a mesma coisa que os gradientes tradicionais, é incluída com um mixin à parte (no caso, o mixin filter-gradient()). Sobre estilos condicionais falarei no próximo ponto.

Folhas de estilo parciais e @import

Tal como no exemplo acima é importada uma biblioteca específica do Compass, também é possível incluir as nossas próprias bibliotecas ou, no caso mais comum, folhas de estilo parciais. O único requisito é que os nomes dos ficheiros comecem por um underscore (_); tudo o que está lá dentro pode ser SCSS válido. Por exemplo, eu tenho sempre um ficheiro _base.scss com mais ou menos o seguinte:

@import "compass/reset";
@import "compass/layout/sticky-footer";
@import "compass/typography/vertical_rhythm";
@import "compass/css3/images";
@import "compass/css3/border-radius";
@import "compass/css3/transition";
@import "compass/css3/transform";
@import "compass/css3/text-shadow";
@import "compass/css3/box-sizing";

$base-font-size: 14px;
$base-line-height: 21px;
$lineHeight: 1.5em;

$fontFamily: 'Cantata One', Georgia, serif;
$alternativeFontFamily: 'Imprima', Verdana, Helvetica, sans-serif;

$normalFontColor: #222;

$baseColor: #E49818;
$lightBaseColor: #FFB334;
$darkBaseColor: #976208;
$lightComplement: #187FE4;
$darkComplement: #004C97;

@include establish-baseline;
@include sticky-footer(54px, "#content", "#footerExpander", "#footer");

* { @include box-sizing("border-box"); }

i,em { font-style: italic; }
b,strong { font-weight: bold; }

Depois, no meu ficheiro principal, é só importar este ficheiro, sem underscore e sem extensão:

@import "base";

O interpretador do SASS incluirá todo aquele código incluído para a CSS correspondente. Alguns casos óbvios para separação são estilos de formulário, estilos de componentes relativamente complexos (calendários salta logo à vista), estilos específicos para dispositivos de dimensões reduzidas e estilos para IE.

Estes últimos dois casos, para além da separação, requerem outro tipo de código. As media queries são comumente usadas directamente nas tags link, assim:

<link rel="stylesheet"
  media="screen and and (max-width: 1024px)"
  href="tablets.css"
/>

No entanto, podem ser usadas dentro das próprias folhas de estilo:

@media screen and (max-width: 1024px)
{
  /* estilos para tablets */
}

@media screen and (max-width: 820px)
{
  /* estilos para smartphones grandes */
}

Juntando isto com a capacidade de importação do SASS, podemos ter um ou mais ficheiros relativos a media queries, tendo apenas o cuidado de os importar no final do ficheiro principal, fazendo com que os estilos sejam herdados correctamente.

A principal vantagem desta técnica é servir apenas um ficheiro, poupando nos requests – infelizmente, usando as tags link, os browsers fazem o download de todas as folhas de estilo, apesar de não cumprirem com a media query. Facilmente se chega a quatro ou cinco requests de CSS, mais uma ou duas caso o browser seja um dos IE.

Esse caso dos IE é ligeiramente mais complicado. O método habitual de incluir folhas de estilo condicionadas a certas versões do IE é usando comentários condicionais, uma especificidade dos IE – neste caso, ainda bem que existe essa especificidade.


O exemplo acima incluiria uma folha de estilos específica quando o browser fosse o Internet Explorer 9 ou inferior (a expressão lte significa less than or equal). Infelizmente, e ao contrário das media queries, é impossível usar este tipo de condições directamente dentro da CSS. Normalmente, isso não representa um problema por aí além. O excesso de requests afectaria cerca de 60% dos utilizadores num site típico, menos (e até muito menos) noutros sites, dependendo do público-alvo. Pessoalmente, estava disposto a assumir essa penalização na esmagadora maioria dos casos, até como dissuassor do uso de browsers foleiros...

Recentemente, tropecei numa técnica para colmatar este pequeno problema; algo tão simples, que só apetece dar o belo do facepalm e exclamar "como é que ninguém tinha pensado nisto antes".

Os comentários condicionais servem para qualquer elemento; isto nem sequer é grande novidade, numa altura ou noutra todos temos usado essa técnica para desenhar alertas específicos para utilizadores do IE (eu até usei essa técnica durante algum tempo aqui no DreamsInCode):


O truque é usar comentários condicionais separados para a abertura e fecho de contentores específicos para cada IE que quisermos apanhar em particular. Só é preciso especial cuidado para que a expressão condicional seja rigorosamente a mesma, para não desbalancear as tags:

<body>
  <!--[if lte IE 9]><div id="ielte9"><![endif]-->
  <!--[if lte IE 8]><div id="ielte8"><![endif]-->
    <!-- Conteúdo normal do site -->
  <!--[if lte IE 8]></div><![endif]-->
  <!--[if lte IE 9]></div><![endif]-->
</body>

O Internet Explorer 9 verá a div com o id ielte9, o IE8 verá essa e ainda a ielte8 e os browsers de outros podutores não verão nenhuma delas. Depois, na CSS, é tão simples como declarar estilos especificados com o id:

.menu
{
  /* formatação normal do menu */
}

#ielte9 .menu
{
  /* formatação do menu para IE9 e inferiores */
}

#ielte8 .menu
{
  /* ainda qualquer coisa mais específica para IE8 e inferiores */
}

Mais uma vez, juntando a esta técnica a capacidade de importação do SASS, podemos ficar com um sistema de vários ficheiros, muito fácil de manter, sem a penalização de vários requests.

A facilidade de uso e manutenção é, aliás, o que de melhor se pode retirar do SASS, sobretudo se for conjugado com o Compass. E isso é tudo o que um webdeveloper pode pedir ao optar por uma tecnologia: menos trabalho de sapa, para se poder concentrar nas grandes opções.

Partilhar no Sapo Links Partilhar no del.icio.us Partilhar no Digg Partilhar no Twitter Partilhar no StumbleUpon Partilhar no MySpace Partilhar no Facebook

Comentários Deixar um comentário

Tem que efectuar login para poder deixar comentários!

Se não está registado, registe-se aqui.
 Doar (via PayPal)
 Categorias
 Arquivo
 Projectos em Destaque
 Últimas Postas no Blog
 Últimos Comentários do Blog