"Cada qual é artífice da própria fortuna." - Júlio César
A frase "dividir para conquistar" atribuída a Napoleão, mas anteriormente utilizada por Júlio César "divide et impera" sofre muitas vezes de um problema de interpretação.
Hoje em dia o termo é usado sem se saber ao certo se significa dividir o inimigo para melhor conquistá-lo ou dividir suas próprias forças para melhor conquistar o inimigo. Embora, César e Napoleão o tenham utilizado no primeiro sentido, ele assume as duas formas no contexto da metodologia de trabalho de um profissional de programação.
Assim, para ser capaz de melhor atacar um problema, o profissional deve ter uma visão do todo para poder dividi-lo em tarefas. Em seguida, deve especializar-se ou procurar especialistas para resolver cada tarefa da melhor e mais rápida forma possível.
No contexto da interface de usuário, o desenvolvimento web se divide em três:
- HTML, usado para definir a estrutura da página;
- CSS, usado para dar estilo e diferenciação visual aos elementos da estrutura;
- JavaScript, adiciona comportamento e dinamicidade à página, tornando-a mais interativa. Do contrário, a página é estática.
Iremos abordar o desacoplamento dessas 3 camadas, através dos seguintes tópicos:
- Mantenha JavaScript Fora do CSS
- Mantenha CSS Fora do JavaScript
- Matenha JavaScript Fora do HTML
- Mantenha HTML Fora do JavaScript
A leitura desses tópicos vai lhe mostrar como o desacoplamento facilita a manutenção de uma aplicação e porque alguns frameworks, como o AngularJS, ganharam popularidade tão rapidamente.
Mantenha JavaScript Fora do CSS
Antigamente, era possível inserir expressões JavaScript dentro do CSS. O exemplo abaixo, por exemplo, seria capaz de alterar a largura de uma determinada div(box), conforme a largura da janela do browser se alterasse.
.box {
width: expression(document.body.offsetWidth + "px");
}
Imagine, porém, que você ou outro desenvolvedor escrevesse por engano a expressão errada e fosse acusado um erro de JavaScript no console, onde você iria procurar por ele?
Você, claro, começaria procurando erros de JavaScript dentro dos scripts da aplicação, quando na verdade eles estariam dentro de um arquivo de estilo CSS!
Dependendo da complexidade da página e do grau de familiaridade com ela, é bem possível que se perca um dia inteiro procurando por algo no lugar errado.
O desacoplamento facilita a identificação de bugs.
Mantenha CSS Fora do JavaScript
Considere os seguintes trechos de códigos responsáveis por alterar o estilo de determinado elemento:
element.style.color = "red";
element.style.left = "10px";
element.style.top = "100px";
element.style.visibility = "visible";
// ou
element.style.cssText = "color: red; left: 10px; top: 100px; visibility: visible";
Os dois trechos de código acima, apesar de aparentemente inofensivos, são ruins. Pelo mesmo motivo que não se especifica mais estilos dentro do próprio HTML, não se deve manipular estilo em JavaScript: a manutenção é muito prejudicada.
Qualquer mudança em uma cor, no tamanho de uma fonte ou qualquer outro atributo, levaria o desenvolvedor primeiro a ficar confuso onde proceder com a alteração, e segundo a correr o risco de realizar a alteração em diversos pontos do código, tornando o trabalho indesejado e altamente braçal.
Isso quer dizer que se deve abandonar totalmente a manipulação de CSS dentro do JavaScript? Não, pois dessa forma estaríamos inviabilizando uma boa porção de dinamicidade na página.
O que estamos querendo dizer aqui é para se manipular CSS, através de classes, conforme abaixo:
// Nativo
element.className += "classeQualquer";
// jQuery
$(element).addClass("classeQualquer");
Mantenha JavaScript Fora do HTML
Uma prática muito comum por volta dos anos 2000 era inserir JavaScript dentro do HTML, é o que se chama de JavaScript obstrusivo. Era comum ver o código a seguir para representar eventos "click" em botões:
<button onclick="facaAlgo()" id="btn">Clique aqui</button>
Esse tipo de prática dificulta a manutenção. Se, por exemplo, a ação do evento mudasse de facaAlgo para facaOutraCoisa, a alteração aconteceria em dois arquivos distintos. Esse tipo de prática também dificulta a detecção de bugs, como é costume quando não se tem uma separação clara de camadas.
O código a seguir, entretanto, não teria esse problema, pois a mudança aconteceria em um único arquivo de extensão js.
function facaAlgo() {
// ...
}
var btn = document.getElementById("btn");
btn.addEventListener("click", facaAlgo);
Mantenha HTML Fora do JavaScript
HTML frequentemente acaba dentro do JavaScript quando usamos a propriedade innerHTML:
var div = document.getElementById("my-div");
div.innerHTML = "<h3>Error</h3><p>Invalid e-mail address.</p>";
Essa prática é um tanto infeliz porque novamente dificulta a detecção de bugs e a manutenção. Além disso, dificulta a separação em especialidades dentro da equipe e torna o código HTML mais sujeito a erros, pois agora é preciso dominar também os caracteres de escape das strings em JavaScript.
Existem duas maneiras principais de contornar esse problema dependendo do seu tipo de aplicação:
1. Carregue do Servidor
Carregar HTML, através de uma solicitação Ajax é prática comum. Sendo mais conveniente nas chamadas "Single Page Applications" do que nas Multiple Page Applications". Vejamos, por exemplo, como você faria para carregar conteúdo HTML ao clicar em um botão, usando jQuery:
$("#button").click(function(e){
$("#box").load("ajax/test.html" );
});
2. Client-Side Templates
Outra maneira de não inserir HTML dentro do código JavaScript é fazendo uso de template engines, como Mustache, Handlebars, Ejs, Jade, etc. O que eles e outros fazem é receber basicamente um objeto como parâmetro e inserir suas propriedades dentro da fôrma(template) do HTML.
Para mais informações e exemplos de utilização de template engines, recomendo a leitura deste artigo que trata especificamente sobre Handlebars, mas dá uma excelente noção de quando, porquê e como devem ser utilizados.
Conclusão
A separação da interface de usuário é tão importante que não a toa surgiram muitos frameworks com a finalidade de facilitar o desenvolvimento front-end seguindo esses padrões. Observe frameworks como Angular, Ember, Knockout, Backbone e tantos outros e observe o quanto eles facilitam a vida do desenvolvedor nesse sentido. Alguns deles possuem mais recursos do que os outros, mas a base do sucesso deles é essa: separação do desenvolvimento em camadas e divisão de responsabilidade.
Veja Também
Continue conhecendo boas práticas de JavaScript em:
- Evite Variáveis Globais;