#angular #angular7
#угловой #angular7
Вопрос:
Я отображаю на странице массив массивов объектов. И у каждого объекта есть событие щелчка. Я хочу заменить столько событий кликов (сейчас это более трех тысяч событий кликов) одним щелчком мыши по оболочке. Например, текущий код
<div *ngFor="var service of services">
<div *ngFor="var cat of service.cats">
<div (click)="catClick(cat)">{{cat.name}}</div>
<div (click)="increaseQuantity(cat)"> </div>
<div (click)="decreaseQuantity(cat)">-</div>
</div>
</div>
Желаемый код
<div (click)="someCommonFunc($event)">
<div *ngFor="var service of services">
<div *ngFor="var cat of service.cats">
<div>{{cat.name}}</div>
<div> </div>
<div>-</div>
</div>
</div>
</div>
Но в event.target я получаю только HTML-код элемента.
Как я могу получить угловой объект, который был привязан к этому html-элементу?
Комментарии:
1. Почему? Какую конкретную проблему вы пытаетесь решить?
2. Я хочу уменьшить количество слушателей
3. Хорошо, но почему? С какой проблемой вы сталкиваетесь с этими слушателями? Доказали ли вы, что эти прослушиватели кликов вызывают серьезные проблемы с производительностью, что оправдывает вашу попытку делать что-то неочевидным, сложным способом?
4. Проблема, как я вижу, заключается не в том, что у вас 3000 событий щелчка, а в том, что вы показываете 1000 элементов на странице, что, в свою очередь, требует этих событий щелчка. Добавьте некоторую фильтрацию и ограничьте количество элементов на странице / экране разумным количеством, например, 50 или даже 100. Существуют различные методы подкачки и элементы управления фильтрацией, которые вы могли бы использовать, чтобы сделать работу более управляемой для пользователя. Никто не хочет прокручивать 1000 элементов, чтобы найти тот, который им нужен.
Ответ №1:
Для достижения ожидаемого результата используйте приведенную ниже опцию использования имени класса и события
- Передайте $event и объект cat во второе событие щелчка цикла
- Используя event.target.className, обновите объект cat
import { Component } from "@angular/core";
@Component({
selector: "app-root",
templateUrl: "./app.component.html",
styleUrls: ["./app.component.css"]
})
export class AppComponent {
title = "CodeSandbox";
displayCat = "";
services = [
{
cats: [{ name: "1aaa1", quantity: 10 }, { name: "1aaa2", quantity: 10 }]
},
{
cats: [{ name: "2aaa1", quantity: 20 }, { name: "2aaa2", quantity: 20 }]
}
];
test(event, cat) {
if (event.target.className === "increase") {
cat.quantity ;
}
if (event.target.className === "decrease") {
cat.quantity--;
}
if (event.target.className === "cat") {
this.displayCat = cat.name;
}
}
}
<div *ngFor="let service of services">
<div
*ngFor="let cat of service.cats"
class="main"
(click)="test($event, cat)"
>
<div class="cat">{{cat.name}}</div>
<div>{{cat.quantity}}</div>
<div class="increase"> </div>
<div class="decrease">-</div>
</div>
</div>
Display Cat Name:
<div>{{displayCat}}</div>
codesandbox — https://codesandbox.io/s/20zzjqzm3n
Ответ №2:
Вы могли бы поместить некоторые атрибуты HTML в элементы. В шаблоне
<div (click)="onClick($event)">
<button *ngFor="let btn of buttons; let i = index"
[attr.data-name]="btn" [attr.data-index]="i">
{{btn}}
</button>
</div>
и в TS
onClick(event) {
console.log(event.target.dataset.name, event.target.dataset.index);
}