Angular 2如何从组件调用指令方法?报onClick未定义错误如何解决
报错原因
报错TypeError: Cannot read property 'onClick' of undefined的核心原因是@ViewChild未匹配到ToggleFullscreenDirective的实例,导致this.appToggleFullscreen为undefined。具体问题出在两处:
- 页面HTML的触发元素未绑定你定义的
appToggleFullscreen指令属性,@ViewChild找不到匹配的指令实例 - 调用逻辑冗余:指令本身已经通过
@HostListener('click')监听了元素点击事件,绑定指令后点击元素会自动触发onClick方法,不需要额外在组件中手动调用
修复方案
方案一(推荐:直接用指令能力,精简代码)
- 修改页面HTML,给触发元素添加
appToggleFullscreen指令,删除冗余的(click)绑定:
<a href="javascript:void(0)" class="text-dark" appToggleFullscreen> <app-feather-icons [icon]="'maximize'"></app-feather-icons> </a>
- 清理组件冗余代码,删除
@ViewChild声明和自定义click方法即可:
export class ReportComponent implements OnInit { constructor() {} ngOnInit() {} }
方案二(适用需要手动触发全屏的业务场景)
如果你的业务逻辑需要在组件代码中主动触发全屏,不依赖用户点击元素,按如下修改:
- 页面HTML保留
appToggleFullscreen指令绑定:
<a href="javascript:void(0)" class="text-dark" appToggleFullscreen> <app-feather-icons [icon]="'maximize'"></app-feather-icons> </a>
- 组件中给
@ViewChild添加配置项(Angular 8+要求),确保能正确获取指令实例:
import { ToggleFullscreenDirective } from '../../../shared/directives/fullscreen.directive'; export class ReportComponent implements OnInit { // 如果要在ngOnInit生命周期前调用指令方法,static设为true,否则设为false @ViewChild(ToggleFullscreenDirective, { static: true }) appToggleFullscreen!: ToggleFullscreenDirective; constructor() {} ngOnInit() {} // 业务逻辑需要触发全屏时调用该方法即可 triggerFullscreen() { if (this.appToggleFullscreen) { this.appToggleFullscreen.onClick(); } } }
额外检查项
如果修改后仍然有问题,检查两点:
- 确认
ToggleFullscreenDirective已在对应模块的declarations数组中声明,如果是定义在共享模块,需要在共享模块的exports数组中导出该指令,同时在使用指令的页面模块导入共享模块 - screenfull的导入可以替换为更规范的ES模块写法:
import * as screenFull from 'screenfull',不需要用require语法
内容的提问来源于stack exchange,提问作者Gowsegan
相关产品推荐
相关产品推荐

