Como obter elemento por classe em JavaScript?

226

Quero substituir o conteúdo de um elemento html, portanto, estou usando a seguinte função para isso:

function ReplaceContentInContainer(id,content) {
   var container = document.getElementById(id);
   container.innerHTML = content;
}

ReplaceContentInContainer('box','This is the replacement text');

<div id='box'></div>

O exemplo acima funciona muito bem, mas o problema é que tenho mais de um elemento html em uma página na qual desejo substituir o conteúdo. Portanto, não posso usar IDs, mas classes. Foi-me dito que o javascript não suporta nenhum tipo de elemento get embutido por função de classe. Então, como o código acima pode ser revisado para fazê-lo funcionar com classes em vez de ids?

PS: Eu não quero usar o jQuery para isso.

Taylor
fonte

Respostas:

198

Este código deve funcionar em todos os navegadores.

function replaceContentInContainer(matchClass, content) {
    var elems = document.getElementsByTagName('*'), i;
    for (i in elems) {
        if((' ' + elems[i].className + ' ').indexOf(' ' + matchClass + ' ')
                > -1) {
            elems[i].innerHTML = content;
        }
    }
}

A maneira como funciona é percorrendo todos os elementos do documento e pesquisando na lista de classes matchClass. Se uma correspondência for encontrada, o conteúdo será substituído.

Exemplo jsFiddle, usando Vanilla JS (ou seja, sem estrutura)

Randy the Dev
fonte
5
+1 - Boa captura dos espaços, sempre esqueço de fazer isso ... roubando isso para minha resposta;) classe é uma palavra reservada em javascript; você não deve usá-lo para um nome de variável, mesmo que ele realmente não cause nenhum dano (ainda).
Dagg Nabbit 28/09/10
1
@no com essa função, você não precisa ter nenhum conteúdo dentro do elemento que deseja substituir. Você pode ter uma string lá ou pode estar vazia. De qualquer maneira, o texto de substituição aparecerá subitamente quando a função for chamada.
Taylor
4
Andrew, não - O uso classcomo um nome de variável não funciona no Safari, portanto, atualmente tem um impacto.
user113716
4
A matriz retornada por getElementsBytagName também possui uma propriedade length, para a qual o teste className / indexOf também é feito. Embora isso não seja um problema nesse caso, um loop for regular seria mais correto.
Wolfgang Stengel
1
em vez de indexOf com espaços, salvar elems[i].className, digitar var cne usar cn && cn.match(new RegExp("(^|\\s)" + matchClass + "(\\s|$)"))funcionaria melhor porque corresponde a qualquer espaço em branco (espaço, espaço sem quebra, tabulação etc.), além de permitir a correspondência entre o primeiro e o último nomes da classe. Exemplo: jsfiddle.net/AXdtH/1636
Supuhstar 30/11
178

Obviamente, todos os navegadores modernos agora oferecem suporte da seguinte maneira mais simples:

var elements = document.getElementsByClassName('someClass');

mas esteja avisado de que não funciona com o IE8 ou antes. Consulte http://caniuse.com/getelementsbyclassname

Além disso, nem todos os navegadores retornarão puro NodeListcomo deveriam.

Você provavelmente ainda está melhor usando sua biblioteca favorita entre navegadores.

Frio frio
fonte
Para o IE8, você pode usar querySelectorAll.
Gras Double
109
document.querySelectorAll(".your_class_name_here");

Isso funcionará em navegadores "modernos" que implementam esse método (IE8 +).

function ReplaceContentInContainer(selector, content) {
  var nodeList = document.querySelectorAll(selector);
  for (var i = 0, length = nodeList.length; i < length; i++) {
     nodeList[i].innerHTML = content;
  }
}

ReplaceContentInContainer(".theclass", "HELLO WORLD");

Se você deseja fornecer suporte para navegadores mais antigos, pode carregar um mecanismo seletor independente como Sizzle (4KB mini + gzip) ou Peppy (10 K mini) e voltar a usá-lo se o método querySelector nativo não for encontrado.

É um exagero carregar um mecanismo seletor para que você possa obter elementos com uma determinada classe? Provavelmente. No entanto, os scripts não são tão grandes e você pode achar o mecanismo seletor útil em muitos outros lugares do seu script.

Cristian Sanchez
fonte
@ Taylor: Eu acho que funciona no IE8 (não 100% de certeza - com preguiça de pesquisar no google). Independentemente disso, adicionei algumas informações sobre compatibilidade com versões anteriores usando mecanismos seletores de terceiros.
Cristian Sanchez
18
document.querySelectorfunciona no IE8 e acima: caniuse.com/queryselector
Zeke
26

Uma maneira simples e fácil

var cusid_ele = document.getElementsByClassName('custid');
for (var i = 0; i < cusid_ele.length; ++i) {
    var item = cusid_ele[i];  
    item.innerHTML = 'this is value';
}
kta
fonte
6

Estou surpreso que não haja respostas usando expressões regulares. Essa é a resposta de Andrew , usando em RegExp.testvez de String.indexOf, pois parece ter um desempenho melhor para várias operações, de acordo com os testes do jsPerf .
Também parece ser suportado no IE6 .

function replaceContentInContainer(matchClass, content) {
    var re = new RegExp("(?:^|\\s)" + matchClass + "(?!\\S)"),
        elems = document.getElementsByTagName('*'), i;
    for (i in elems) {
        if (re.test(elems[i].className)) {
            elems[i].innerHTML = content;
        }
    }
}

replaceContentInContainer("box", "This is the replacement text.");

Se você procurar a (s) mesma (s) classe (s) com freqüência, poderá aprimorá-la ainda mais, armazenando as expressões regulares (pré-compiladas) em outro local e passando-as diretamente para a função, em vez de uma string.

function replaceContentInContainer(reClass, content) {
    var elems = document.getElementsByTagName('*'), i;
    for (i in elems) {
        if (reClass.test(elems[i].className)) {
            elems[i].innerHTML = content;
        }
    }
}

var reBox = /(?:^|\s)box(?!\S)/;
replaceContentInContainer(reBox, "This is the replacement text.");
afsantos
fonte
4

Isso deve funcionar em praticamente qualquer navegador ...

function getByClass (className, parent) {
  parent || (parent=document);
  var descendants=parent.getElementsByTagName('*'), i=-1, e, result=[];
  while (e=descendants[++i]) {
    ((' '+(e['class']||e.className)+' ').indexOf(' '+className+' ') > -1) && result.push(e);
  }
  return result;
}

Você deve poder usá-lo assim:

function replaceInClass (className, content) {
  var nodes = getByClass(className), i=-1, node;
  while (node=nodes[++i]) node.innerHTML = content;
}
Dagg Nabbit
fonte
3

var elems = document.querySelectorAll('.one');

for (var i = 0; i < elems.length; i++) {
    elems[i].innerHTML = 'content';
};

Roger Causto
fonte
4
Isso não é realmente uma resposta. Por favor, tente explicar seu código . Além disso, é basicamente uma versão mais compacta de outra resposta a essa pergunta publicada há 5 anos.
21815 Helmbert
Não sei qual é o problema. Esta resposta está bem. Não há comentários ... e o que? Esta não é uma regra de ouro. E o que você quer comentar aqui? E mas é um código legível?
AntiCZ
3

Suponho que essa não era uma opção válida quando isso foi solicitado originalmente, mas agora você pode usá-lo document.getElementsByClassName('');. Por exemplo:

var elements = document.getElementsByClassName(names); // or:
var elements = rootElement.getElementsByClassName(names);

Veja a documentação MDN para mais.

thornjad
fonte
0

Eu acho algo como:

function ReplaceContentInContainer(klass,content) {
var elems = document.getElementsByTagName('*');
for (i in elems){
    if(elems[i].getAttribute('class') == klass || elems[i].getAttribute('className') == klass){
        elems[i].innerHTML = content;
    }
}
}

trabalharia

KeatsKelleher
fonte
1
se você tiver apenas um punhado de elementos em sua página, caso contrário, essa é a solução O (N)
jwl
getAttribute ( 'class') parece funcionar em todos, mas IE, então getAttribute ( 'className') funciona no IE
KeatsKelleher
0

O jQuery lida com isso com facilidade.

let element = $(.myclass);
element.html("Some string");

Ele altera todos os elementos .myclass para esse texto.

Daniel Høifødt
fonte
PS: a pergunta diz ".Eu não quero usar o jQuery para isso."
Julian
Ok, eu não vi isso.
Daniel Høifødt
-15

Quando alguns elementos não possuem ID, eu uso o jQuery assim:

$(document).ready(function()
{
    $('.myclass').attr('id', 'myid');
});

Pode ser uma solução estranha, mas talvez alguém ache útil.

O Krotek
fonte
3
Se houver vários elementos com classe myclass, todos eles obterão o ID myid, mas os IDs devem ser únicos! Além disso, o OP diz explicitamente para evitar o jQuery.
Oriol 22/06
1
Não é difícil adicionar uma cláusula foreach () e aumentar o ID, se você tiver vários elementos da mesma classe. Eu adicionei esta solução como uma alternativa para aqueles que podem usar o jQuery. OP já tem um monte de respostas adequadas de qualquer maneira :-)
O Krotek