我正在使用此教程来创建自定义上下文菜单。 我正在显示列表中的项目,我希望当用户单击这些项目时,显示它们的索引。目前,右键单击任何项目会显示最后一个索引,例如,如果我的列表有 3 个项目,则单击任何项目会显示 2! 如何显示每个项目的正确索引?
这是我的代码:
<div *ngFor="let item of items; let i = index" (contextmenu)="displayContextMenu($event); false">
<span> {{item}}</span>
<app-context-menu
*ngIf="rightClickMenuItems.length > 0 && isDisplayContextMenu"
[ngStyle]="getRightClickMenuStyle()"
[contextMenuItems]="rightClickMenuItems"
(onContextMenuItemClick)="handleMenuItemClick($event, i)"
></app-context-menu>
</div>
ts 文件:
items = ["item0","item1","item2"];
isDisplayContextMenu!: boolean;
rightClickMenuItems: Array<ContextMenu> = [];
rightClickMenuPositionX!: number;
rightClickMenuPositionY!: number;
displayContextMenu(event: any) {
this.isDisplayContextMenu = true;
this.rightClickMenuItems = [
{
menuText: 'Print index',
menuEvent: 'Handle print index',
},
];
this.rightClickMenuPositionX = event.clientX;
this.rightClickMenuPositionY = event.clientY;
}
handleMenuItemClick(event: any, index: number) {
switch (event.data) {
case this.rightClickMenuItems[0].menuEvent:
this.printIndex(index);
break;
}
}
printIndex(index: number){
alert(index);
}
@HostListener('document:click')
documentClick(): void {
this.isDisplayContextMenu = false;
}
getRightClickMenuStyle() {
return {
position: 'fixed',
left: `${this.rightClickMenuPositionX}px`,
top: `${this.rightClickMenuPositionY}px`
}
}
上下文菜单组件:
.html:
<ng-container>
<div>
<div *ngFor="let menuItem of contextMenuItems; index as i"
(click)="onContextMenuClick($event, menuItem.menuEvent)">
{{ menuItem.menuText }}
</div>
</div>
</ng-container>
.ts
import { Component, Input, Output, EventEmitter } from '@angular/core';
import { ContextMenu } from '../../_models/contextMenu.model';
import { NgIf, NgFor } from '@angular/common';
@Component({
selector: 'app-context-menu',
templateUrl: './context-menu.component.html',
styleUrls: ['./context-menu.component.css'],
standalone: true,
imports: [NgIf, NgFor]
})
export class ContextMenuComponent {
@Input() contextMenuItems!: Array<ContextMenu>;
@Output() onContextMenuItemClick: EventEmitter<any> = new EventEmitter<any>();
onContextMenuClick(event: any, data: any): any {
this.onContextMenuItemClick.emit({
event,
data,
});
}
}
型号:
export interface ContextMenu {
menuText: any;
menuEvent: any;
}
context-menu
移到 *ngFor
之外,因为您只需要一个表格的上下文菜单。data-id
数据属性 来识别选择了哪个项目。代码
<div *ngFor="let item of items; let i = index" (contextmenu)="displayContextMenu($event); false"
[attr.data-id]="item">
<span> {{item}}</span>
我们可以访问属性来标识哪个项目被选择,我们可以只存储选定的索引,这里有两个选项将其存储在主组件中,或者您可以只将其存储在上下文菜单中。
const id = event.target.parentElement.dataset.id ? event.target.parentElement.dataset.id : 事件.目标.数据集.id; const findIndex = this.items.findIndex((x) => x === id); if (foundIndex > -1) { this.index = 找到索引;
最后,我们可以使用警报打印索引!
this.printIndex(this.index);
main.ts
import { CommonModule } from '@angular/common';
import { Component, HostListener } from '@angular/core';
import { bootstrapApplication } from '@angular/platform-browser';
import 'zone.js';
import {
ContextMenu,
ContextMenuComponent,
} from './context-menu/context-menu.component';
@Component({
selector: 'app-root',
standalone: true,
imports: [CommonModule, ContextMenuComponent],
template: `
<div *ngFor="let item of items; let i = index" (contextmenu)="displayContextMenu($event); false"
[attr.data-id]="item">
<span> {{item}}</span>
</div>
<app-context-menu
*ngIf="rightClickMenuItems.length > 0 && isDisplayContextMenu"
[ngStyle]="getRightClickMenuStyle()"
[contextMenuItems]="rightClickMenuItems"
(onContextMenuItemClick)="handleMenuItemClick($event)"
></app-context-menu>
`,
})
export class App {
items = ['item0', 'item1', 'item2'];
index = -1;
isDisplayContextMenu!: boolean;
rightClickMenuItems: Array<ContextMenu> = [];
rightClickMenuPositionX!: number;
rightClickMenuPositionY!: number;
displayContextMenu(event: any) {
const id = event.target.parentElement.dataset.id
? event.target.parentElement.dataset.id
: event.target.dataset.id;
const foundIndex = this.items.findIndex((x) => x === id);
if (foundIndex > -1) {
this.index = foundIndex;
this.isDisplayContextMenu = true;
this.rightClickMenuItems = [
{
menuText: 'Print index',
menuEvent: 'Handle print index',
},
];
this.rightClickMenuPositionX = event.clientX;
this.rightClickMenuPositionY = event.clientY;
}
}
handleMenuItemClick(event: any) {
switch (event.data) {
case this.rightClickMenuItems[0].menuEvent:
this.printIndex(this.index);
break;
}
}
printIndex(index: number) {
alert(index);
}
@HostListener('document:click')
documentClick(): void {
this.isDisplayContextMenu = false;
}
getRightClickMenuStyle() {
return {
position: 'fixed',
left: `${this.rightClickMenuPositionX}px`,
top: `${this.rightClickMenuPositionY}px`,
};
}
}
bootstrapApplication(App);
上下文菜单
import { Component, Input, Output, EventEmitter } from '@angular/core';
import { NgIf, NgFor } from '@angular/common';
export interface ContextMenu {
menuText: any;
menuEvent: any;
}
@Component({
selector: 'app-context-menu',
template: `
<ng-container>
<div>
<div
*ngFor="let menuItem of contextMenuItems; index as i"
(click)="onContextMenuClick($event, menuItem.menuEvent)"
>
{{ menuItem.menuText }}
</div>
</div>
</ng-container>
`,
standalone: true,
imports: [NgIf, NgFor],
})
export class ContextMenuComponent {
private id!: string;
@Input() contextMenuItems!: Array<ContextMenu>;
@Output() onContextMenuItemClick: EventEmitter<any> = new EventEmitter<any>();
onContextMenuClick(event: any, data: any): any {
this.onContextMenuItemClick.emit({
event,
data,
});
}
}