angularnativescriptangular2-nativescriptnativescript-angular

How do I share a component to every screen in Nativescript using Angular


I am trying to add a top action bar to every screen in the app but does not appear. I am using nativescript with Angular. I have setup a SharedComponentsModule that has the HeaderComponent and I export the headercomponent. Then I import the SharedComponentsModule in the app.module file. With this, I expect it to work in ever screen but it does not. What could be the problem? Doesn't Nativescript allow sharing components among screens or how am I supposed to do it?

The attached pictures show the header am trying to add to every screen. screen1 screen2

The SharedComponentsModule:

import { NgModule, NO_ERRORS_SCHEMA } from '@angular/core';
import { NativeScriptCommonModule } from 'nativescript-angular/common';
import { HeaderComponent } from './header/header.component';

@NgModule({
  declarations: [HeaderComponent],
  imports: [NativeScriptCommonModule],
  exports: [HeaderComponent],
  schemas: [NO_ERRORS_SCHEMA],
})
export class SharedComponentsModule {}

AppModule

import { NgModule, NO_ERRORS_SCHEMA } from '@angular/core';
import { NativeScriptModule } from 'nativescript-angular/nativescript.module';
import { AppRoutingModule } from './app-routing.module';

import { AppComponent } from './app.component';
import { SharedComponentsModule } from './components/shared-components.module';

@NgModule({
  bootstrap: [AppComponent],
  imports: [SharedComponentsModule, NativeScriptModule, AppRoutingModule],
  declarations: [AppComponent],
  schemas: [NO_ERRORS_SCHEMA],
})
export class AppModule {}

header-component.html


<ActionBar class="action-bar" (loaded)="onActionBarLoaded($event)">
  <GridLayout
    columns="auto,*,auto"
    orientation="horizontal"
    ios:padding="0 10"
    height="100%"
    width="100%"
  >
    <Label
      *ngIf="isBackIcon"
      ios:horizontalAlignment="left"
      android:horizontalAlignment="left"
      row="0"
      col="0"
      class="fas back"
      text="&#xf060;"
      (tap)="goBack()"
    >
    </Label>
    <Image
      ios:horizontalAlignment="{{isBackIcon ? 'center' : 'left'}}"
      android:horizontalAlignment="{{isBackIcon ? 'center' : 'left'}}"
      class="logo"
      row="0"
      col="1"
      src='~/assets/images/logo1.png'></Image>
  </GridLayout>

  <ActionItem
    text="Home"
    ios.position="right"
    android.position="popup"
    (tap)="onHome()">
  </ActionItem>
  <ActionItem
    text="About"
    ios.position="right"
    android.position="popup"
    (tap)="onAbout()">
  </ActionItem>

  <ActionItem
    text="My Account"
    ios.position="right"
    android.position="popup"
    (tap)="onAccount()">
  </ActionItem>
  <ActionItem
    text="FAQ"
    ios.position="right"
    android.position="popup"
    (tap)="onFaq()">
  </ActionItem>
  <ActionItem
    text="Terms and Conditions"
    ios.position="right"
    android.position="popup"
    (tap)="onTerms()">
  </ActionItem>
  <ActionItem
    text="Sign Out"
    ios.position="right"
    android.position="popup"
    (tap)="onSignout()">
  </ActionItem>
</ActionBar>

header-component.ts

import { Component, Input, OnInit } from '@angular/core';
import { RouterExtensions } from 'nativescript-angular/router';

declare const android;

@Component({
  selector: 'Header',
  templateUrl: './header.component.html',
  styleUrls: ['./header.component.css'],
})
export class HeaderComponent implements OnInit {
  @Input() isBackIcon: boolean;

  constructor(private routerExtensions: RouterExtensions) {}

home-component.html

<Header [isBackIcon]="backIcon"></Header>

<GridLayout>
  <label text="Some test text"></label>
</GridLayout>

Thanks in advance.


Solution

  • So I managed to solve this issue by removing module files from every screen component and declared all of them in one shared-components file. Then I imported this file in the app.module.ts file. So in the whole project I only have two modules. So when am routing in the app-routing.module file, route to the screen component and not the module. This worked well and I have the header component on every screen.

    app-routing.module.ts

    { path: '', redirectTo: '/home', pathMatch: 'full' },
      {
        path: 'home',
        component: HomeComponent,
      },
      {
        path: 'about',
        component: AboutComponent,
      },
      {
        path: 'terms',
        component: TermsComponent,
      },
      {
        path: 'account',
        component: AccountComponent,
      },
      {
        path: 'edit-account',
        component: EditAccountComponent,
      },