Basically I'm looking for a way to implement a counterpart to Angular 1.x ngInit
directive.
I'm aware of ngOnInit
hook and the fact that it is the recommended place for initialization code. I consider ngInit
directive a quick, declarative way to prototype or fix a component that shouldn't be generally used in well-written production code (although a developer has the right to choose what's best for him/her).
Doing something like that in init
dummy directive
<p [init]="foo = 1; bar()"><p>
evaluates the expression more than one time and causes
Template parse errors:
Parser Error: Bindings cannot contain assignments
error.
In Angular 1.x it could be done just with
$parse($attrs.init)($scope)
How can Angular 2 parser be used and possibly extended to evaluate foo = 1; bar()
template expression on component initialization?
The ng-init Directive is used to initialize AngularJS Application data. It defines the initial value for an AngularJS application and assigns values to the variables. The ng-init directive defines initial values and variables for an AngularJS application.
The ngInit directive allows you to evaluate an expression in the current scope. This directive can be abused to add unnecessary amounts of logic into your templates. There are only a few appropriate uses of ngInit : aliasing special properties of ngRepeat , as seen in the demo below.
Calling a function or initializing a single value on page load in AngularJS is quite easy. AngularJS provides us with a dedicated directive for this specific task. It's the ng-init directive. Example 1: In this example, we will call a function to initialize a variable on page load.
Naming Convention: *[name of directive] — Upper camel case is used for the directive class, while lower camel case is used for the directive's name. What sets them apart from other directives in Angular 2: Reshape DOM structure by adding or removing existing DOM elements and do not have templates.
Just a Workaround ( Plunker Demo ), see estus's answer for a solution
init
Directive:@Directive({
selector: '[init]',
inputs: ['init']
})
export class InitDir {
init;
ngOnChanges() { // `ngOnInit` if you want it to run just once
if(this.init){
let iife = function(str){ return eval(str); }.call(this.init[0], this.init[1]);
}
}
}
@Component({
selector: 'my-app',
template: `
<div>
<h2 [init]="[this, 'this.name = 1; this.bar();']">Hello {{name}}</h2>
</div>
`,
})
export class App {
constructor() {
this.name = 'Angular2 (Release Candidate!)'
}
bar() {
alert('Yo Bar!');
}
}
This can be achieved with a directive:
@Directive({ selector: '[initialize]' })
class InitializeDirective {
@Output() initialize = new BehaviorSubject();
}
The expected use is:
<div (initialize)="initViaMethodCall(); foo = 'init via assignment'"></div>
<ng-template (initialize)="bar = 'init with no extra markup'"></template>
{{ foo }}
{{ bar }}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With