Angular2 如何获取所有带有特定类名的元素

54

有人可以帮忙解决如何在Angular 2中找到特定类名的“所有”元素吗? 我认为这很简单,但给我带来了比预期更多的问题。

<span class="classImLookingFor">foo</span>
<span class="classImLookingFor">Voo</span>
<span class="classImLookingFor">Moo</span>
我认为执行以下操作将返回所有具有"classImLookingFor"类的元素,但它只返回第一个实例。
constructor(private renderer: Renderer){}
ngAfterViewInit(){
 const el = this.renderer.selectRootElement('.classImLookingFor');
 this.renderer.setElementAttribute(el, 'tabindex', 0);
}

之后,我的标记看起来像这样。

<span class="classImLookingFor" tabindex="0">foo</span>
<span class="classImLookingFor">Voo</span>
<span class="classImLookingFor">Moo</span>

看起来我应该能创建一个Renderer数组,但那似乎也行不通。我需要操纵每个具有该类名的元素。


4
您可以使用 document.querySelectorAll('.classImLookingFor') 这段代码。 - Aravind
正是我想要的。它完美地工作。不过,由于某种原因,document.getElementsByClassName 对我没有用。感谢您的快速回复。我把它弄得太复杂了。 - dekaha1
你能给我的回答点个赞吗?因为它对你有所帮助。 - Aravind
7个回答

92

这样不会返回DOM中的所有元素吗?有没有办法只返回由我所在的Angular组件生成的元素?

您需要...

  1. constructor中注入ElementRef

  2. constructor(private renderer: Renderer, private elem: ElementRef){}
    
  3. 使用querySelectorAll API查找您要搜索的元素。

  4. ngAfterViewInit(){
        // you'll get your through 'elements' below code
        let elements = this.elem.nativeElement.querySelectorAll('.classImLookingFor');
    }
    

@Aravind提供的答案对性能来说不是最好的,因为它会搜索整个DOM。

这个解决方案只会搜索当前组件内的DOM。


2
这是在Angular中获取渲染值(querySelectorAll)的实际方法。 - SHUBHASIS MAHATA
对我没有效果。使用“document”按预期工作,但这种方法不行。很不幸,因为我可以看到以这种方式做的好处。 - JeneralJames
@JeneralJames,我认为它对你不起作用,因为你正在搜索elementRef之外的元素,而this.elem.nativeElement.querySelectorAll仅在其中搜索。 - Shlomi Aharoni
1
使用 ElementRef<HTMLElement> 来保证类型安全。 - CularBytes

17

Angular 10+文档与SSR的兼容性,导入:

import { DOCUMENT } from '@angular/common'

然后注入:

constructor(@Inject(DOCUMENT) private _document: HTMLDocument) {
    }

你可以像这样在你的组件/指令中使用:

doSomething(): void {
 this._document.querySelectorAll('.classImLookingFor')
}

13

回答评论对OP有帮助。

你应该使用

document.querySelectorAll('.classImLookingFor')

4
这个函数会返回 DOM 中的所有元素吗?有没有办法只返回由我所在的 Angular 组件生成的元素? - Skorunka František
@SkorunkaFrantišek,你是正确的,请检查这个答案 - Paritosh
我点赞了,因为如果你想引用文档中在当前 Angular 组件之外的元素,这将非常有用。 - Yvonne Aburrow

5
这可能有点简化你的应用场景,但你是否有使用原生DOM函数的任何理由呢?像这样:
var domRepresentation = document.getElementsByClassName('classImLookingFor');
var angularElement = angular.element(domRepresentation);

修改后的注释 - Aravind
第一次阅读时我没有注意到这个评论,对此感到抱歉。 - Billy Barry
3
我很新于 Stack Overflow 并发现没有回答。最佳做法是先评论而不是直接回答问题吗,@Aravind? - Billy Barry
6
angular 是从哪里来的?是指 AngularJS 还是 Angular2+? - Christian

2

有多种方法可以实现,但Angular 9+版本提供的最新方法是:

1.在Angular中导入Inject和DOCUMENT。

import {Inject } from '@angular/core';
import { DOCUMENT } from '@angular/common';

2. 然后在所需类的构造函数中创建一个引用。

constructor(@Inject(DOCUMENT) private _document: HTMLDocument) {}

3.使用所有javascript方法作为变量。

selectElement(): void {
 this._document.querySelector('#mySelectedId');
}

2
使用Angular / common中的此“DOCUMENT”和本地document.*有什么好处? - Phoenix404

0

使用案例; 按下Esc键 -> 移除标记行的边框

enter image description here

  resetMarkedRows():void{
    const rowContainer = document.getElementById('row-container');
    //get row node list
    const rowNodes = rowContainer && rowContainer.querySelectorAll('.row-outer');
    //convert node list to an array
    const rows = Array.from(rowNodes) as HTMLElement[];
    const markedRows = rows.filter((row:HTMLElement)=>{
      if(row.style.border == "1px solid rgb(0, 136, 255)"){
        return row
      }
    });
    markedRows[0].style.border = "none";
  }

-4

你需要在Angular中使用DOM

var element=document.getElementsByClassName("X").item(0);

这对我有效!


2
可能在AngularJS中有效,但在Angular 2+中无效。 - Yvonne Aburrow
4
你不应该直接访问DOM,这会破坏Angular对平台的抽象。应该使用ViewChild和/或Renderer2。 - Looted

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接