0

I have two components app and child. in child component I have button on click of which I am calling a function (function name is assigned to a variable which make it dynamic) which is defines in app component. But this is not working. Any help?

app.ts

selector: 'my-app',
template: `
  <div>
    <h2>Hello {{name}}</h2>
    <child-comp></child-comp>
    <p>{{data}}</p>
  </div>
`,
})
export class App {
  name:string;
  data: string;
  constructor() {
    this.name = 'Angular2'
  }
  dummyFunction(){  // I want to call this function
      data = "function called";
  }
}

Child.ts

@Component({
  selector: 'child-comp',
  template: `
    <input type="button" value="click me" (click) = [funcName]()>  // Here I am calling the function which is assign to a variable
  `,
})
export class ChildComp {
  funcName: string;
  constructor() {
    funcName = 'dummyFunction';  // assigning function name to variable
  }
}

Attaching Plunker

2 Answers 2

3

I don't think you can do exactly what you are describing, but can achieve the same thing using the Output decorator and EventEmitter as described in the documentation for parent-child component communication.

Your child component can emit an event, buttonClicked below, and the parent component (i.e. app) can bind to that event with the required callback (i.e. dummyFunction())

App component

@Component({
  selector: 'my-app',
  template: `
    <div>
      <h2>Hello {{name}}</h2>
      <child-comp (buttonClicked)="dummyFunction()"></child-comp>
      <p>{{data}}</p>
    </div>
  `,
})
export class App {
  name:string;
  data: string;
  constructor() {
    this.name = 'Angular2'
  }

  dummyFunction(){ // I want to call this function
    this.data = "function called";
  }
}

And child component

import {Component, Output, EventEmitter} from '@angular/core'

@Component({
  selector: 'child-comp',
  template: `
    <input type="button" value="click me" (click) = "onClick($event)"> // Here I am calling the function which is assign to a variable
  `,
})
export class ChildComp {

  @Output() buttonClicked = new EventEmitter();
  constructor() {
  }

  onClick($event){
    this.buttonClicked.emit($event);
  }
}
Sign up to request clarification or add additional context in comments.

Comments

1

if call only child method

Child.ts

@Component({
  selector: 'child-comp',
  template: `
    <input type="button" value="click me" (click)="this[funcName]()">  // Here I am calling the function which is assign to a variable
  `,
})
export class ChildComp {
  funcName: string;
  constructor() {
    this.funcName = 'dummyFunction';  // assigning function name to variable
  }
  dummyFunction() {
    console.log('do something')
  }
}

or

@Component({
  selector: 'child-comp',
  template: `
    <input type="button" value="click me" (click)="funcName()"> // callhere
  `,
})
export class ChildComp {
  funcName: Fn;
  constructor() {
    this.funcName = this.dummyFunction.bind(this);  // assigning function to variable
  }
  dummyFunction() {
    console.log('do something')
  }
}

if you need communicate from parent and child:

@Component({
  selector: 'child-comp',
  template: `
    <input type="button" value="click me" (click)="funcName()"> // callhere
  `,
})
export class ChildComp {
  @Input()
  funcName: Fn;
  constructor() {
  }
}

@Component({
selector: 'my-app',
template: `
  <div>
    <h2>Hello {{name}}</h2>
    <child-comp [funcName]="dummyFunction"></child-comp>
    <p>{{data}}</p>
  </div>
`,
})
export class App {
  name:string;
  data: string;
  constructor() {
    this.name = 'Angular2';
    this.dummyFunction = this.dummyFunction.bind(this);
  }
  dummyFunction(){  // I want to call this function
      data = "function called";
  }
}

or using Output

import {Component, Output, EventEmitter } from '@angular/core'

@Component({
  selector: 'child-comp',
  template: `
    <input type="button" value="click me" (click)="onClick($event)">
  `,
})
export class ChildComp {

  @Output() eventName = new EventEmitter();
  constructor() {

  }
  onClick(e) {
    // do something here
    this.eventName.emit(e);
  }
}

parent:

@Component({
selector: 'my-app',
template: `
  <div>
    <h2>Hello {{name}}</h2>
    <child-comp (eventName)="dummyFunction()"></child-comp>
    <p>{{data}}</p>
  </div>
`,
})
export class App {
  name:string;
  data: string;
  constructor() {
    this.name = 'Angular2';
  }
  dummyFunction(){  // I want to call this function
      data = "function called";
  }
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.