page - meta service angular




Angular 2 Использовать компонент из другого модуля (6)

У меня есть приложение Angular 2 (версия 2.0.0 - окончательная версия), созданное с помощью angular-cli.

Когда я создаю компонент и добавляю его в AppModule объявлений AppModule , все хорошо, все работает.

Я решил разделить компоненты, поэтому создал TaskModule и компонент TaskCard . Теперь я хочу использовать TaskCard в одном из компонентов AppModule (компонент Board ).

AppModule:

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { FormsModule } from '@angular/forms';
import { HttpModule } from '@angular/http';

import { AppComponent } from './app.component';
import { BoardComponent } from './board/board.component';
import { LoginComponent } from './login/login.component';

import { MdButtonModule } from '@angular2-material/button';
import { MdInputModule } from '@angular2-material/input';
import { MdToolbarModule } from '@angular2-material/toolbar';

import { routing, appRoutingProviders} from './app.routing';
import { PageNotFoundComponent } from './page-not-found/page-not-found.component';

import { UserService  } from './services/user/user.service';
import { TaskModule } from './task/task.module';


@NgModule({
  declarations: [
    AppComponent,
    BoardComponent,// I want to use TaskCard in this component
    LoginComponent,
    PageNotFoundComponent
  ],
  imports: [
    BrowserModule,
    FormsModule,
    HttpModule,
    MdButtonModule,
    MdInputModule,
    MdToolbarModule,
    routing,
    TaskModule // TaskCard is in this module
  ],
  providers: [UserService],
  bootstrap: [AppComponent]
})
export class AppModule { }

TaskModule:

import { NgModule } from '@angular/core';
import { TaskCardComponent } from './task-card/task-card.component';

import { MdCardModule } from '@angular2-material/card';

@NgModule({
  declarations: [TaskCardComponent],
  imports: [MdCardModule],
  providers: []
})
export class TaskModule{}

Весь проект доступен по https://github.com/evgdim/angular2 (папка kanban-board)

Что мне не хватает? Что мне нужно сделать, чтобы использовать TaskCardComponent в BoardComponent ?


(Угловой 2 - Угловой 7)

Компонент может быть объявлен только в одном модуле. Чтобы использовать компонент из другого модуля, вам необходимо выполнить две простые задачи:

  1. Экспортировать компонент в первый модуль
  2. Импортируйте первый модуль во второй модуль

1-й модуль:

Имеем компонент (назовем его «ImportantCopmonent»), который мы хотим повторно использовать на странице 2-го модуля.

@NgModule({
declarations: [
    FirstPage,
    ImportantCopmonent // <-- Enable using the component html tag in current module
],
imports: [
  IonicPageModule.forChild(NotImportantPage),
  TranslateModule.forChild(),
],
exports: [
    FirstPage,
    ImportantCopmonent // <--- Enable using the component in other modules
  ]
})
export class FirstPageModule { }

2-й модуль:

Повторно использует «ImportantCopmonent», импортируя FirstPageModule

@NgModule({
declarations: [
    SecondPage,
    Example2ndComponent,
    Example3rdComponent
],
imports: [
  IonicPageModule.forChild(SecondPage),
  TranslateModule.forChild(),
  FirstPageModule // <--- this Imports the source module, with its exports
], 
exports: [
    SecondPage,
]
})
export class SecondPageModule { }

@yurzui у вас есть правильное решение и спасибо за объяснение.

У меня была проблема и эта строка:

Экспорт: [Компонент] решил.


Вы должны export его из вашего NgModule :

@NgModule({
  declarations: [TaskCardComponent],
  exports: [TaskCardComponent],
  imports: [MdCardModule],
  providers: []
})
export class TaskModule{}

Обратите внимание, что для создания так называемого «функционального модуля» вам необходимо импортировать в него CommonModule . Итак, код инициализации вашего модуля будет выглядеть так:

import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';

import { TaskCardComponent } from './task-card/task-card.component';
import { MdCardModule } from '@angular2-material/card';

@NgModule({
  imports: [
    CommonModule,
    MdCardModule 
  ],
  declarations: [
    TaskCardComponent
  ],
  exports: [
    TaskCardComponent
  ]
})
export class TaskModule { }

Более подробная информация доступна здесь: https://angular.io/guide/ngmodule#create-the-feature-module


Основное правило здесь таково:

Селекторы, которые применяются во время компиляции шаблона компонента, определяются модулем, который объявляет этот компонент, и транзитивным закрытием экспортов импорта этого модуля.

Итак, попробуйте экспортировать его:

@NgModule({
  declarations: [TaskCardComponent],
  imports: [MdCardModule],
  exports: [TaskCardComponent] <== this line
})
export class TaskModule{}

Что я должен экспортировать?

Экспортируйте декларируемые классы, на которые компоненты в других модулях должны ссылаться в своих шаблонах. Это ваши публичные занятия. Если вы не экспортируете класс, он остается закрытым, видимым только для других компонентов, объявленных в этом модуле.

В тот момент, когда вы создаете новый модуль, ленивый или нет, любой новый модуль и что-то в него объявляете, этот новый модуль находится в чистом состоянии (как сказал Уорд Белл в https://devchat.tv/adv-in-angular/119-aia-avoiding-common-pitfalls-in-angular2 )

Angular создает транзитивный модуль для каждого из @NgModule s.

Этот модуль собирает директивы, которые либо импортированы из другого модуля (если транзитивный модуль импортированного модуля имеет экспортированные директивы), либо объявлены в текущем модуле .

Когда шаблон углового компиляции, принадлежащий модулю X использует те директивы, которые были собраны в X.transitiveModule.directives .

compiledTemplate = new CompiledTemplate(
    false, compMeta.type, compMeta, ngModule, ngModule.transitiveModule.directives);

https://github.com/angular/angular/blob/4.2.x/packages/compiler/src/jit/compiler.ts#L250-L251

Таким образом, согласно изображению выше

  • YComponent не может использовать ZComponent в своем шаблоне, потому что массив directives Transitive module Y не содержит ZComponent потому что YModule не импортировал ZModule , переходный модуль которого содержит ZComponent в массиве ZComponent .

  • В шаблоне XComponent мы можем использовать ZComponent потому что Transitive module X имеет массив директив, который содержит ZComponent потому что XModule импорта YModule ( YModule ), который экспортирует модуль ( ZModule ), который экспортирует директиву ZComponent

  • В шаблоне AppComponent мы не можем использовать XComponent потому что AppModule импортирует XModule но XModule не экспортирует XComponent .

Смотрите также


РЕШЕНО, КАК ИСПОЛЬЗОВАТЬ КОМПОНЕНТ, ЗАЯВЛЕННЫЙ В МОДУЛЕ В ДРУГОМ МОДУЛЕ.

Основано на объяснении Ройи Намира (Большое спасибо). Отсутствует часть для повторного использования компонента, объявленного в модуле, в любом другом модуле, пока используется отложенная загрузка.

1-й: экспортировать компонент в модуль, который содержит его:

@NgModule({
  declarations: [TaskCardComponent],
  imports: [MdCardModule],
  exports: [TaskCardComponent] <== this line
})
export class TaskModule{}

2-й: в модуле, где вы хотите использовать TaskCardComponent:

import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';
import { MdCardModule } from '@angular2-material/card';

@NgModule({
  imports: [
   CommonModule,
   MdCardModule
   ],
  providers: [],
  exports:[ MdCardModule ] <== this line
})
export class TaskModule{}

Таким образом, второй модуль импортирует первый модуль, который импортирует и экспортирует компонент.

Когда мы импортируем модуль во второй модуль, нам нужно экспортировать его снова. Теперь мы можем использовать первый компонент во втором модуле.





angular-module