Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Angular 2 - Multiple components in any layout on different static pages

Tags:

angular

I have a bunch of static pages that use various components that are placed wherever a HTML designer likes. e.g. within any page on a WordPress site.

Though the sample components shown here are simple Panels, but in reality there are all sorts of components, e.g. Search, Lists, Editors, Views etc...

Currently they have been done on lots of Wordpress Sites where each and every page can have totally different layouts. In the past we used Angular 1.5 where the WP developer you could just put our app tag up near the body and then any widget (we have about 30) could be placed 1 or more times in any page.

Components can be re-used so making the components root components via the bootstrap[] property does not make sense as you can only use a root component once on a page. As seen in my second example.

Technique 1

Here is a screenshot and Plunker for the first setup. Notice that I have 4 area's in which I place 3 components with component 1 being reused.

This Example is done by laying out the components inside a single root component, which is impractical for my use case where Wordpress Pages will have totally different layout and composition requirements. .

Plunkr

enter image description here

Technique 2

I have tried using a technique where each widget is bootstrapped as a root component, based on this post Bootstrapping Multiple Applications Sprinkling Angular 2 components inside a non-angular page.

But when I use this technique the 2nd instance of a widget does not load. AKA widget 1.

Plunkr

See example with bootstrapping

enter image description here

Technique 2 - Has further problems

If you have bootstrapped 3 root components, you MUST use all of them otherwise Angular throws up an error about the root component that you did not use.

Plunker

enter image description here

Technique 3

The use of <ng-content></ng-content> does not seem to work root components.

See: Angular2 Root Component with ng-content

like image 350
David Cruwys Avatar asked Oct 28 '16 05:10

David Cruwys


Video Answer


1 Answers

For this kind of widgets the better is to have an ng2 application instantiated per each widget like Bootstrap multiples applications. I did post a possible solution there.

I do implement an ApplicationFactory which create a dynamic selector like:

moduleFactory(selector: string, childModule : ModuleWithProviders) {

  @Component({
    selector, // dynamic selector
   ...
  })
  export class AppComponent implements AfterViewInit{
    constructor(resolver: ComponentFactoryResolver){}
    ngAfterViewInit() {
      // Cretate a Child components dynamic 
      // mapping from childModule::[bootstrap] components decoration
    }
 }

 @NgModule({
   declarations: [
     AppComponent
   ],
   imports: [
     BrowserModule,
     FormsModule,
     HttpModule
   ],
   bootstrap: [AppComponent]
 })
 class AppModule { }

  platformBrowserDynamic()
      .bootstrapModule(AppModule, {providers: childModule.providers});
}

In then in ngAfterViewInit you may create a dynamic component using a ComponentFactoryResolver

This is not an ideal solutions but it works

like image 75
user55993 Avatar answered Nov 15 '22 04:11

user55993