Posso usar classes CSS não existentes?

260

Eu tenho uma tabela onde eu mostrar / ocultar uma coluna completa por jQuery através de uma classe CSS que não existe:

<table>
   <thead>
      <tr>
         <th></th>
         <th class="target"></th>
         <th></th>
      </tr>
   </thead>
   <tbody>
      <tr>
         <td></td>
         <td class="target"></td>
         <td></td>
      </tr>
      <tr>
         <td></td>
         <td class="target"></td>
         <td></td>
      </tr>
   </tbody>
</table>

Com este DOM, posso fazer isso em uma linha via jQuery: $('.target').css('display','none');

Isso funciona perfeitamente, mas é válido usar classes CSS que não estão definidas? Devo criar uma classe vazia para isso?

<style>.target{}</style>

Existem efeitos colaterais ou existe uma maneira melhor de fazer isso?

totymedli
fonte
9
Não vejo nada de errado com isso, embora eu o tenha tornado parte da folha de estilo, se possível, em vez de usar .css, os estilos configurados com .css são muito difíceis de substituir sem causar outros problemas, por isso tendem a evitá-los.
Kevin B
8
como uma observação lateral que você pode querer usar .toggle(), é um pouco mais curta no seu código.
Math chiller
4
No Visual Studio + ReSharper, se você usar uma classe que não está definida, ele receberá um aviso, o que é útil se eu tiver apenas um erro de digitação, mas for irritante em situações como essa. Nesse caso, você tem a opção de adicionar o estilo vazio ou desativar o aviso (ou simplesmente ignorá-lo) - pessoalmente, apenas adiciono o estilo vazio. Não sei se algum outro IDE se comporta da mesma forma.
Joe Enos
8
Não é apenas possível, mas é explicitamente recomendado por alguns. Como você targeté para fins de javascript, muitas pessoas usam o prefixo js-para essas classes, ou seja js-target. BTW: Alvo é uma espécie de um nome ruim;) Para ler mais, consulte: philipwalton.com/articles/decoupling-html-css-and-javascript
k0pernikus
1
stackoverflow.com/questions/2832117/… é mais ou menos uma duplicata disso, sem o equívoco.
precisa saber é o seguinte

Respostas:

491

"Classe CSS" é um nome impróprio; classé um atributo (ou uma propriedade, em termos de script) que você atribui aos elementos HTML. Em outras palavras, você declarar classes em HTML, não CSS, por isso, no seu caso a classe "alvo" faz em exist verdade sobre os elementos específicos, e sua marcação é perfeitamente válido como ela é.

Isso não significa necessariamente que você precisa ter uma classe declarada no HTML antes de poder usá-la também em CSS. Veja o comentário de ruakh. A validade ou não de um seletor depende inteiramente da sintaxe do seletor e o CSS possui seu próprio conjunto de regras para lidar com erros de análise , nenhum dos quais diz respeito à marcação. Essencialmente, isso significa que HTML e CSS são completamente independentes um do outro no aspecto de validade. 1

Depois de entender isso, fica claro que não há efeito colateral de não definir uma .targetregra na sua folha de estilo. 2 Ao atribuir classes aos seus elementos, você pode fazer referência a esses elementos em uma folha de estilo, script ou ambos. Nenhum dos dois depende do outro. Em vez disso, os dois se referem à marcação (ou, mais precisamente, à sua representação DOM). Esse princípio se aplica mesmo se você estiver usando JavaScript para aplicar estilos, como você faz em uma linha única do jQuery.

Quando você escreve uma regra CSS com um seletor de classe, tudo o que diz é "Quero aplicar estilos a elementos que pertencem a essa classe". Da mesma forma, quando você escreve um script para recuperar elementos com um determinado nome de classe, está dizendo "Quero fazer coisas com elementos que pertencem a essa classe". Se há ou não são elementos que pertencem à classe em questão é uma questão separada completamente.


1 É também por isso que um seletor de ID do CSS corresponde a todos os elementos com o ID fornecido, independentemente de o ID aparecer exatamente uma vez ou várias vezes (resultando em um documento HTML não conforme).

2 A única situação em que sei onde é necessária uma regra CSS vazia como essa é quando alguns navegadores se recusam a aplicar outras regras corretamente como resultado de um bug; criar uma regra vazia fará com que essas outras regras sejam aplicadas por algum motivo. Veja esta resposta para um exemplo de um erro desse tipo. No entanto, isso está do lado do CSS e, portanto, não deve ter nada a ver com a marcação.

BoltClock
fonte
5
Levei séculos para perceber que as aulas não tinham nada a ver com CSS. Mas na mesma época todo mundo percebeu e microformatos apareceram.
Konrad Rudolph
13
+1, embora essa resposta possa ser considerada implícita, incorretamente, que CSS pode se referir apenas a classes que realmente ocorrem no HTML. Na verdade, é bastante comum que um site tenha CSS em todo o site usado em todas as páginas, mesmo que algumas das classes a que ele se refere não apareçam em todas as páginas. (Por exemplo, o site pode ter estilo personalizado para links externos, a.extlinkou outros enfeites, mesmo que algumas páginas não contêm quaisquer ligações externas.)
ruach
1
@ruakh: Excelente ponto, obrigado. Não consegui encontrar uma maneira de encaixá-lo na minha resposta breve e original sem desviar o assunto, mas vejo como o uso do termo dependência pode ter causado essa impressão, então mudei um pouco. Dito isto, adicionei uma nota de rodapé referenciando seu comentário, além de elaborar mais.
BoltClock
66

Não há efeitos negativos para usar classes que não possuem estilos. De fato, isso faz parte da utilidade do CSS, que é desacoplado da marcação e pode estilizar ou não estilizar elementos / classes / etc. como necessário.

Não pense nelas como "classes CSS". Pense nelas como "classes" que o CSS também usa, se necessário.

David
fonte
11
+1 em "Não pense nelas como 'classes CSS'. Pense nelas como 'classes' que o CSS também usa se for necessário "
laike9m
48

De acordo com a especificação HTML5 :

Um atributo de classe deve ter um valor que seja um conjunto de tokens separados por espaço, representando as várias classes às quais o elemento pertence. ... Não há restrições adicionais sobre os tokens que os autores podem usar no atributo class, mas os autores são incentivados a usar valores que descrevem a natureza do conteúdo, em vez de valores que descrevem a apresentação desejada do conteúdo.

Além disso, na versão 4 :

O atributo de classe tem várias funções em HTML:

  • Como seletor de folhas de estilo (quando um autor deseja atribuir informações de estilo a um conjunto de elementos).
  • Para processamento de uso geral por agentes do usuário.

Seu caso de uso se enquadra no segundo cenário, o que o torna um exemplo legítimo do uso de um atributo de classe.

Vitalii Fedorenko
fonte
13
+1 para citar as especificações relevantes. Eu esqueci muito de fazer isso.
BoltClock
40

Você pode usar uma classe que não tem estilos, isso é HTML totalmente válido.

Uma classe referenciada em um arquivo CSS não é uma definição de classe, é usada como regra de seleção para fins de estilo.

Curt
fonte
25

Quando você usa um nome de classe em JavaScript, ele não olha o CSS para encontrar essa classe. Parece diretamente no código HTML.

Tudo o que é necessário é que o nome da classe esteja no HTML. Não precisa estar no CSS.

De fato, muitas pessoas pensam que é realmente uma boa idéia manter classes separadas em uso com CSS e Javascript , pois isso permite que seus designers e codificadores trabalhem independentemente, sem se atrapalhar usando as classes uns dos outros.

(observe que o parágrafo acima é obviamente mais aplicável a projetos maiores, portanto, não pense que você precisa ir ao extremo se estiver trabalhando sozinho; mencionei isso para enfatizar que os dois podem ser totalmente separados )

Spudley
fonte
13

Você pode usar classes CSS sem usá-lo, mas sugiro que se você estiver adicionando classes CSS apenas para o código JavaScript / jQuery, prefixe-o js-YourClassNamepara que os desenvolvedores de front-end nunca usem essas classes para estilizar os elementos. Eles devem entender que essas classes podem ser removidas a qualquer momento.

Aamir Afridi
fonte
10

No momento em que você adicionar a classe em seu HTML, a classe será definida, para que sua solução esteja completamente correta

koningdavid
fonte
7
Usar a classe em HTML não a define. Eu diria que a definição é irrelevante: não há penalidade pelo uso de classes indefinidas.
JAL
10

Não é necessário definir classes CSS na sua folha de estilo. Deve funcionar muito bem. No entanto, adicioná-lo não fará mal.

Rameez
fonte
Não estou dizendo para adicionar esses estilos, cabe a ele se ele quiser, se ele planeja apoiar esses estilos, por que não? de qualquer forma, obrigado por voto desnecessário para baixo :) #
227
Você disse "isso ... não fará mal", mas acabará.
Pavlo
sim, não fará mal. se ele tiver sentidos para adicionar esses estilos vazios, obviamente terá sentidos para gerenciá-los. Obviamente eu não vou adicionar ... nem eu estou aconselhando a adicionar.
Rameez
8

Uma coisa que ninguém aqui mencionou completamente é que o JavaScript (auxiliado pelo jQuery neste caso) não pode modificar diretamente a folha de estilos em cascata de um documento. O css()método do jQuery apenas altera o conjunto de stylepropriedades dos elementos correspondentes . CSS e JavaScript não têm nenhuma relação com esse aspecto.

$('.target').css('display','none');não altera sua .target { }declaração CSS. O que aconteceu aqui é que qualquer elemento com um class"destino" agora se parece com isso:

<element class="target" style="display:none;"></element>

Existem efeitos colaterais causados ​​por não pré-definir uma regra de estilo CSS? Nenhuma.

Existe uma maneira melhor de fazer isso? Em termos de desempenho, sim, existe!

Como o desempenho pode ser melhorado?

Em vez de modificar diretamente o styleelemento de cada elemento, você pode predefinir uma nova classe e adicioná-la aos elementos correspondentes usandoaddClass() (outro método jQuery).

Com base na presente JSPerf pré-existente que compara css()com addClass(), podemos ver que addClass()é realmente muito mais rápido:

css () vs addClass ()

Como podemos implementar isso sozinhos?

Primeiramente, podemos adicionar nossa nova declaração CSS:

.hidden {
    display: none;
}

Seu HTML permaneceria o mesmo, essa classe predefinida está simplesmente no local para uso posterior.

Agora podemos modificar o JavaScript para usar addClass():

$('.target').addClass('hidden');

Ao executar esse código, em vez de modificar diretamente a stylepropriedade de cada um dos elementos "target" correspondentes, essa nova classe agora será adicionada:

<element class="target hidden"></element>

Com a nova classe "oculta", esse elemento herdará o estilo declarado em seu CSS e seu elemento será definido para não ser mais exibido.

James Donnelly
fonte
Bom conselho. Raramente existe um bom motivo para usar em .css()vez de alternar as classes IMO.
BoltClock
6

Como é mencionado por muitos outros, sim, o uso de classes sem CSS atribuído é perfeitamente válido e, em vez de pensar nelas como 'classes CSS', você deve simplesmente reconhecer a semântica da classe e ID como grupos e elementos individuais, respectivamente.

Eu queria participar porque senti que um ponto importante não foi levantado, dado o exemplo. Se você precisar manipular visualmente um comprimento variável de elementos (nesse caso, você está usando linhas de tabela), sempre faz sentido reconhecer que o custo de fazê-lo através do Javascript pode ser potencialmente muito caro (por exemplo, se você tiver milhares de linhas).

Nessa situação, digamos que sabemos que a coluna 2 sempre tem o potencial de ser oculta (é uma função consciente da sua tabela), então faz sentido projetar um estilo CSS para lidar com esse caso de uso.

table.target-hidden .target { display: none; }

Então, em vez de usar JS para percorrer os elementos N de localização do DOM, simplesmente precisamos alternar uma classe em uma (nossa tabela).

$("table").addClass("target-hidden")

Ao atribuir um ID à tabela, isso seria ainda mais rápido e você poderia até se referir à coluna usando o :nth-childseletor que reduziria ainda mais sua marcação, mas não posso comentar sobre eficiência. Outra razão para fazer isso é que eu odeio o estilo embutido e me esforçarei ao máximo para erradicá-lo!

Ian Clark
fonte
1
1 para os "grupos individuais e elementos" e para o uso eficiente da estrutura do documento
deltab
5

Isso não terá efeito se você aplicar uma classe em um elemento HTML, e essa classe não estiver definida em CSS. É uma prática comum e, como Aamir afridi disse, se você estiver usando classes apenas para js, é uma boa prática prefixá-las com js-.

Não é válido apenas para calsses, mas também para o atributo id de elementos html.

Altaf Hussain
fonte
4

Não há nenhum problema em usar classes para apenas consultar elementos. Eu costumava dar o sys-prefixo a esses nomes de classe (por exemplo, vou nomear sua classe sys-target) para distingui-los das classes usadas para estilizar. Esta foi uma convenção usada por alguns desenvolvedores da Microsoft no passado. Também notei uma prática crescente de usar o js-prefixo para esse fim.

Se você não estiver familiarizado com o uso de classes para outros fins que não o estilo, recomendo usar o plug- in Role.js jQuery, que permite atingir o mesmo objetivo usando o roleatributo, portanto, você pode escrever sua marcação como <td role="target">e consultá-la usando $("@target"). A página do projeto tem uma boa descrição e exemplos. Eu uso esse plug-in para grandes projetos, porque eu realmente gosto de manter as classes apenas para fins de estilo.

Ashraf Sabry
fonte
3

Consulte o mecanismo de validação do jQuery . Mesmo lá também usamos classes inexistentes para adicionar regras de validação aos atributos HTML . Portanto, não há nada errado em usar classes que não são realmente declaradas em uma folha de estilo.

dhruvin
fonte