Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I pass specific bindings to ng-outlet components brought in by the component router in Angular 1.5?

I'd like to be able to pass parameters to child components brought in with ng-outlet. But I'm not sure how to do it.

Here's an example of my component bindings:

app.component('profile', {
  bindings: {
    section: '=',
    currentUser: '<'
  },
...

Normally I'd invoke this like so:

<profile section="$ctrl.bio" current-user="$ctrl.selectedUser"></profile>

But instead I have this:

<ng-outlet></ng-outlet>

And a router that passes the profile in.

 $routeConfig: [
        { path: '/Profile/:id', name: 'Profile', component: 'profile' }]

So how the blazes do I pass other essential bindings, perhaps bindings that can't be encoded into the URL, to this component??

Thanks, help is very much appreciated

EDIT: I've been asked to provide a more specific example of what I'd like to do.

I thought the conceptual issue was fairly clear, but here's a particular case where passing route parameters is clearly insufficient. Say at my App component level I have an event callback function, onDeleteItem(id)

How do I replicate

bindings: {
    onDeleteItem: "&"
}

...

<some-component on-delete-item="$ctrl.onDeleteItem(id)"></some-component>

with an ng-outlet?

like image 707
tcmoore Avatar asked Mar 17 '16 01:03

tcmoore


2 Answers

I looked on the docs and saw this for one of the components used in the router

bindings: { $router: '<' }

So I was thinking well if that binding can get filled in, then why can't we pass data for the other bindings, but I looked through the source of the component router, and I actually don't see a way to pass data that way. This is because here it looks like it's specially handling passing in the $router, but I don't think the template is modified after that:

activate(instruction) {
    ...
    this.controller.$$template = '<' + dashCase(componentName) + ' $router="::$$router"></' + dashCase(componentName) + '>';
    ...
};


I will say though, you are supposed to be able to pass data through to the component using

$routeConfig: [
    { path: '/Profile/:id', name: 'Profile', component: 'profile', data: { item1: 'item1'} }]

and then injecting RouteData in the constructor of the component, but I think this is only in angular 2, because I didn't see implementation for it the in the angular 1 router.


So based on the research I've done, I don't think you can, or it's difficult. Also, related: How to inject data into Angular2 component created from a router and https://github.com/angular/angular/issues/4452

like image 65
CShark Avatar answered Sep 22 '22 11:09

CShark


Even through ngOutlet, you can use the require argument like specified here https://docs.angularjs.org/guide/component to require a parent component. This way, you can communicate with the parent component from the child component (even so the parent component calls the child component through ngOutlet). This enables the communication from child => parent. Regarding parent => child, you could still use the same technic, even if it feels a bit awkward (you call the parent from the child to get what you need...). Maybe something more standard already exists, or will be implemented soon.

like image 23
Christophe Vidal Avatar answered Sep 19 '22 11:09

Christophe Vidal