다른 모듈의 컴포넌트 사용


199

angular-cli로 생성 된 Angular 2.0.0 앱이 있습니다.

구성 요소를 작성하고 추가 할 때 AppModule 선언 배열에 모두 작동합니다.

구성 요소를 분리하기로 결정 했으므로 TaskModule및 구성 요소를 만들었습니다 TaskCard. 이제 TaskCard구성 요소 중 하나 AppModule에서Board 구성 요소) 구성 .

앱 모듈 :

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 { }

작업 모듈 :

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?

답변:


389

여기서 주요 규칙은 다음과 같습니다.

컴포넌트 템플릿 컴파일 중에 적용 할 수있는 선택기는 해당 컴포넌트를 선언하는 모듈과 해당 모듈 가져 오기 내보내기의 전이 폐쇄에 의해 결정됩니다.

따라서 내보내십시오.

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

무엇을 내 보내야합니까?

다른 모듈의 구성 요소가 해당 템플릿에서 참조 할 수 있어야하는 선언 가능한 클래스를 내 보냅니다. 이들은 당신의 공개 수업입니다. 클래스를 내 보내지 않으면 비공개로 유지되며이 모듈에 선언 된 다른 구성 요소에만 표시됩니다.

새 모듈을 만들거나, 새 모듈을 만들거나, 새 모듈을 만들고 그 모듈에 아무것도 선언하면 새 모듈은 깨끗한 상태를 갖습니다 (Ward Bell이 https://devchat.tv/adv-in-angular/119 에서 말했듯이) -aia-avoiding- 공통 함정-각도 2 )

Angular 는 각각에 대해 전이 모듈 을 만듭니다 @NgModule.

이 모듈 은 다른 모듈 (가져온 모듈의 전이 모듈이 지시어를 내 보낸 경우)에서 가져 오거나 현재 모듈에 선언 된 지시문을 수집합니다 .

angular가 모듈에 속하는 템플릿을 컴파일 할 때 X.transitiveModule.directivesX 에서 수집 된 지시문이 사용됩니다 .

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그의 이적 모듈 포함 ZComponentexportedDirectives배열입니다.

  • XComponent템플릿 우리가 사용할 수 ZComponent있기 때문에 Transitive module X포함 지시어 배열이 ZComponent있기 때문에 XModule수입 (모듈 YModule(수출 모듈 있음) ZModule) 수출 지시어가ZComponent

  • 가져 오기는 하지만 가져 오기를 하지 않기 때문에 AppComponent템플릿 내에서 사용할 수 없습니다 .XComponentAppModuleXModuleXModuleXComponent

또한보십시오


13
가져 오기 모듈의 경로 정의에서이 "TaskCardComponent"를 어떻게 사용합니까?
jackOfAll

17
정말 좋은 답변입니다. 도면을 작성 했습니까? 그렇다면 말이 없습니다. 모든 사람이 답을 구하는 것은 아닙니다. 감사합니다
Royi Namir 2016

4
예 @Royi이 내 사진입니다 : 그것은에서 소스 코드를 기반으로 github.com/angular/angular/blob/master/packages/compiler/src/...
yurzui

@yuruzi 저는 레퍼런스없이 직접 DOM 노드를 통과 할 수 stackoverflow.com/questions/47246638/... plnkr.co/edit/DnnjFBa3HLzFKNIdE4q5?p=preview
KARTY

@ yurzui ... 나는 YComponent가 ZModule을 어떻게 내보낼 수 있는지 이해할 수 없습니다. .module.ts) [기본 질문이라면 저를
보내십시오

42

당신은 export그것에서해야합니다 NgModule:

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

2
TaskModule을 AppModule에서 가져올 때까지 작동합니다. TaskModule이 지연로드되면 실패합니다.
Arun

40

(앵귤러 2-앵귤러 7)

컴포넌트는 단일 모듈에서만 선언 할 수 있습니다. 다른 모듈의 구성 요소를 사용하려면 두 가지 간단한 작업을 수행해야합니다.

  1. 다른 모듈에서 컴포넌트 내보내기
  2. 다른 모듈을 현재 모듈로 가져 오기

첫 번째 모듈 :

컴포넌트를 가져 오십시오 ( "ImportantCopmonent"라고 함). 두 번째 모듈 페이지에서 재사용하고 싶습니다.

@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 { }

두 번째 모듈 :

FirstPageModule을 가져 와서 "ImportantCopmonent"를 재사용

@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 { }

2

소위 "기능 모듈"을 만들려면 그 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


0

다른 모듈에서 사용하려는 것이 무엇이든 내보내기 배열 에 넣으십시오 . 이처럼

 @NgModule({
  declarations: [TaskCardComponent],
  exports: [TaskCardComponent],
  imports: [MdCardModule]
})

0

하나의 크고 훌륭한 접근 방법은에서 모듈을 NgModuleFactory로드하는 것입니다.이를 호출하여 다른 모듈 안에 모듈을로드 할 수 있습니다.

constructor(private loader: NgModuleFactoryLoader, private injector: Injector) {}

loadModule(path: string) {
    this.loader.load(path).then((moduleFactory: NgModuleFactory<any>) => {
        const entryComponent = (<any>moduleFactory.moduleType).entry;
        const moduleRef = moduleFactory.create(this.injector);
        const compFactory = moduleRef.componentFactoryResolver.resolveComponentFactory(entryComponent);
        this.lazyOutlet.createComponent(compFactory);
    });
}

나는 여기 에서 이것을 얻었다 .


NgModuleFactoryLoader는 이제 더 이상 사용되지 않으므로이 작업을 수행하는 가장 좋은 대체 방법은 무엇입니까?
Muzaffar Mahmood

-2

다른 모듈의 모듈에 선언 된 구성 요소를 사용하는 방법

Royi Namir의 설명을 바탕으로합니다 (감사합니다). 지연로드가 사용되는 동안 다른 모듈의 모듈에 선언 된 구성 요소를 재사용하기위한 누락 된 부분이 있습니다.

1 차 : 컴포넌트를 포함하는 모듈에서 컴포넌트를 내 보냅니다.

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

두 번째 : 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{}

이와 같이 두 번째 모듈은 구성 요소를 가져오고 내보내는 첫 번째 모듈을 가져옵니다.

두 번째 모듈에서 모듈을 가져 오면 다시 내 보내야합니다. 이제 두 번째 모듈의 첫 번째 구성 요소를 사용할 수 있습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.