:: ng-deepをどこでどのように使用しますか?


95

私はAngular4を初めて使用するので::ng-deep、Angular4で使用する方法と場所を誰かに説明してもらえますか?

実際、親コンポーネントから子コンポーネントのCSSプロパティの一部を上書きしたいと思います。さらに、IE11でサポートされていますか?


/deep/::ng-deepは両方とも非推奨であるため、この回答stackoverflow.com/a/49308475/2275011とコメントを参照して詳細と解決策を確認することをお勧めします。
フェリー

回答:


99

通常、 /deep/ “shadow-piercing”コンビネータを使用して、スタイルをに強制することができますchild components。このセレクターにはエイリアス>>>があり、:: ng-deepという別のセレクターがあります。

以降/deep/ combinator廃止されている、それが使用することをお勧めします::ng-deep

例えば:

<div class="overview tab-pane" id="overview" role="tabpanel" [innerHTML]="project?.getContent( 'DETAILS')"></div>

そして css

.overview {
    ::ng-deep {
        p {
            &:last-child {
                margin-bottom: 0;
            }
        }
    }
}

子コンポーネントに適用されます


IE11をサポートしていますか?
Jeyabalan Thavamani 2017年

2
Angularが解析を行うので、互換性について心配する必要はありません。
Simon_Weaver 2018年

子コンポーネント専用ですか?私が覚えているように、そして別のコメントで見るように、それはコンポーネント外のdom要素にも当てはまります。
ヤヤ

親コンポーネントも実行していることを確認できます...ケースがあっただけで、それに悩まされました。
Shadoweb

74

使用法

::ng-deep>>>および/deep/特定のCSSルールのビューカプセル化を無効にします。つまり、コンポーネントのHTMLにないDOM要素にアクセスできます。たとえば、Angular Material(またはこのような他のサードパーティライブラリ)を使用している場合、生成された要素の一部はコンポーネントの領域外にあり(ダイアログなど)、それらの要素に直接アクセスしたり、通常のCSSを使用したりすることはできません。仕方。これらの要素のスタイルを変更する場合は、次の3つのいずれかを使用できます。

::ng-deep .mat-dialog {
  /* styles here */
}

今のところ、Angularチームは、EMULATEDビューのカプセル化でのみ「深い」操作を行うことを推奨しています。

廃止

「深い」の操作は、実際にされている非推奨あまりにも、しかし角度は前処理をサポートしていので、それは今のために働いて静止画(断るために急いではありません::ng-deep、今日見とる非推奨慣行を最初に)。

とにかく、この方法に従う前に、ビューのカプセル化アプローチを無効にすることを検討することをお勧めします(これも理想的ではなく、スタイルが他のコンポーネントに漏れる可能性があります)が、場合によっては、より良い方法です。ビューのカプセル化を無効にすることにした場合は、特定のクラスを使用してCSSルールの交差を回避し、最後にスタイルシートの混乱を回避することを強くお勧めします。コンポーネントの.tsファイルで直接無効にするのは本当に簡単です。

@Component({
  selector: '',
  template: '',
  styles: [''],
  encapsulation: ViewEncapsulation.None  // Use to disable CSS Encapsulation for this component
})

ビューのカプセル化の詳細については、この記事を参照しください。


3
ビューのカプセル化を無効にすると、コンポーネント内のすべてのCSSがグローバルに適用されます。
ヴェドラン

19
使用しないでくださいViewEncapsulation.None!これらのスタイルが他のコンポーネントに漏れる可能性があるため、多くの損傷が発生します。
アレックスクラウス

1
@AlexKlaus、同意します、それが私が答えで述べた理由です、それは理想的ではありません。実際、AngularMaterialコンポーネントに共有の繰り返し可能なスタイルを適用するために一度だけ使用しました。カプセル化を無効にしようとすると、ある時点で混乱する可能性があります。このオプションについて知っておくのは良いことですが、これが必要かどうか絶対に確信が持てない場合は使用しないでください。
商業自殺

34

::ng-deep親がカプセル化されたcssクラスであることを要求することにより、コンポーネントの子のみに制限することの重要性を強調します。

これが機能するため::ng-deepには、親の後にを使用することが重要です。そうしないと、コンポーネントがロードされた瞬間に同じ名前のすべてのクラスに適用されます。

コンポーネントcss:

.my-component ::ng-deep .mat-checkbox-layout {
    background-color: aqua;
}

コンポーネントテンプレート:

<h1 class="my-component">
    <mat-checkbox ....></mat-checkbox>
</h1>

結果の(Angularで生成された)css:

.my-component[_ngcontent-c1] .mat-checkbox-layout {
    background-color: aqua;
}

編集:

:host新しいcssクラスを作成する代わりに、キーワードを使用して同じ動作を実現できます。

:host ::ng-deep .mat-checkbox-layout

7
男、あなたの答えはmy-component ::ng-deep...ちょうど私の日を救った。私は一日中、ng-deepを使用してコンポーネントにスタイルを適用しようとし、アプリケーション全体からすべてのコンポーネントをオーバーライドしていました。
クリスティアーノボンバザール

2
注目に値する:「指定されたスタイルを現在のコンポーネントとそのすべての子孫にスコープするために(グローバルではない)、:: ng-deepの前に:hostセレクターを必ず含めてください。」From:angular.io/guide/component-styles
StvnBrkdll

1
@ CristianoBombazar-:hostキーワードでも同じ動作が得られます-わかりやすくするために回答にメモを追加しました。
Vedran

25

角度ガイドの:host-contextすぐ上::ng-deepにある説明を見逃さないようにしてください:https//angular.io/guide/component-styles。今まで見逃していたので、もっと早く見たかったです。

::ng-deepコンポーネントを作成しておらず、そのソースにアクセスできない場合に必要になることがよくありますが、作成:host-contextする場合は非常に便利なオプションです。

たとえば<h1>、設計したコンポーネント内に黒いヘッダーがあり、暗いテーマの背景に表示されたときにそれを白に変更できるようにしたいです。

ソースにアクセスできなかった場合は、親のcssでこれを行う必要があるかもしれません。

.theme-dark widget-box ::ng-deep h1 { color: white; }

ただし、代わり、コンポーネント内で:host-contextこれを行うことができます。

 h1 
 {
     color: black;       // default color

     :host-context(.theme-dark) &
     {
         color: white;   // color for dark-theme
     }

     // OR set an attribute 'outside' with [attr.theme]="'dark'"

     :host-context([theme='dark']) &
     {
         color: white;   // color for dark-theme
     }
 }

これにより、コンポーネントチェーン内の任意の場所が検索され、.theme-dark見つかった場合はcssがh1に適用されます。これは、::ng-deep多くの場合必要であるものの、多少アンチパターンであることに依存しすぎることに対する優れた代替手段です。

この場合、&h1(sass / scssの動作方法)に置き換えられるため、「通常」とテーマ/代替のcssを互いに隣接して定義できます。これは非常に便利です。

の正しい数を取得するように注意してください:。以下のために::ng-deep2とのためにそこにいる:host-contextだけで。


親コンポーネントから:host(.theme-dark)継承theme-darkしたくない場合にも使用できます。これは完全にあなたのサイトのCSSデザインに依存します。また、属性は非常に便利であり、cssだけで洗練された方法で組み合わせることができます:host([theme='dark']:not([dayofweek='tuesday'))
Simon_Weaver 2018

また、これは通常のcssルールに従っているため、.theme-lightクラスを持つコンテナ内に上記のようなコンポーネント(ホストコンテキストcssを使用)がある場合、これはコンテナ内にネストされ、.theme-dark引き続きを取得してtheme-dark適用します。 css。ただし、これは「modernizr」タイプのクラス、またはテーマをグローバルに1回だけ設定する場合に最適なソリューションです。
Simon_Weaver

:: ng-deepの代わりに:host-contextを使用できますか?

@eddy今は眠くてこれを完全に考えることはできませんが、host-contextはng-deepに似ていますが、DOMツリーを下ではなく上に移動します。だから、絶対に同じではないのですが、あなたは可能性
Simon_Weaver

2

ただの更新:

非推奨のように見える::ng-deep代わりに使用する必要があります/deep/

ドキュメントごと:

シャドウピアスの子孫コンビネータは非推奨になり、主要なブラウザとツールからサポートが削除されます。そのため、Angularでのサポートを終了する予定です(/ deep /、>>>、:: ng-deepの3つすべて)。それまでは、ツールとの互換性を高めるために:: ng-deepを使用することをお勧めします。

あなたはここでそれを見つけることができます


5
このテキストでは、:: ng-deepも非推奨であると明確に述べています:「Angularでのサポートを終了する予定です(/ deep /、>>>、:: ng-deepの3つすべて)」。
adripanico 2018

-2

:: ng-deepは注意して使用してください。アプリ全体でこれを使用して、マテリアルデザインツールバーの色をアプリ全体で異なる色に設定しましたが、アプリがテスト中にツールバーの色が互いにステップしていることがわかりました。これらのスタイルがグローバルになるためです。この記事を参照してください。これ は、他のコンポーネントにブリードしない実用的なコードソリューションです。

<mat-toolbar #subbar>
...
</mat-toolbar>

export class BypartSubBarComponent implements AfterViewInit {
  @ViewChild('subbar', { static: false }) subbar: MatToolbar;
  constructor(
    private renderer: Renderer2) { }
  ngAfterViewInit() {
    this.renderer.setStyle(
      this.subbar._elementRef.nativeElement, 'backgroundColor', 'red');
  }

}
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.