ng-if
とng-show
/ の違いを理解しようとしng-hide
ていますが、同じように見えます。
どちらを使用するかを選択する際に留意すべき違いはありますか?
ng-if
とng-show
/ の違いを理解しようとしng-hide
ていますが、同じように見えます。
どちらを使用するかを選択する際に留意すべき違いはありますか?
回答:
ngIf
ディレクティブ削除したり再作成式に基づいてDOMツリーの部分を。ngIf
評価に割り当てられた式がfalse値に評価される場合、要素はDOMから削除されます。そうでない場合、要素のクローンがDOMに再挿入されます。
<!-- when $scope.myValue is truthy (element is restored) -->
<div ng-if="1"></div>
<!-- when $scope.myValue is falsy (element is removed) -->
<div ng-if="0"></div>
ngIf
スコープを使用して要素が削除されると、要素が復元されるときに破棄され、新しいスコープが作成されます。内部で作成されたngIf
スコープは、プロトタイプ継承を使用して親スコープから継承します。
ngModel
内で使用しngIf
て、親スコープで定義されたJavaScriptプリミティブにバインドする場合、子スコープ内の変数に加えられた変更は、親スコープの値に影響しません。たとえば、
<input type="text" ng-model="data">
<div ng-if="true">
<input type="text" ng-model="data">
</div>
この状況を回避し、子スコープ内から親スコープのモデルを更新するには、オブジェクトを使用します。
<input type="text" ng-model="data.input">
<div ng-if="true">
<input type="text" ng-model="data.input">
</div>
または、$parent
親スコープオブジェクトを参照する変数:
<input type="text" ng-model="data">
<div ng-if="true">
<input type="text" ng-model="$parent.data">
</div>
ngShow
ディレクティブ表示または非表示に提供される発現に基づいて、指定されたHTML要素ngShow
の属性。要素は、ng-hide
CSSクラスを要素から削除または追加することによって表示または非表示になります。.ng-hide
CSSクラスはAngularJSで事前定義及び(使用noneに表示スタイルを設定された!important
フラグ)。
<!-- when $scope.myValue is truthy (element is visible) -->
<div ng-show="1"></div>
<!-- when $scope.myValue is falsy (element is hidden) -->
<div ng-show="0" class="ng-hide"></div>
ときngShow
に表現評価さは、false
その後、ng-hide
CSSクラスが追加されるclass
原因となる要素の属性には、隠されたになるために。の場合true
、ng-hide
CSSクラスが要素から削除され、要素が非表示に表示されなくなります。
data.input
にオブジェクトがある場合、どのように/なぜそれが機能するかです...しかしdata
、モデルの中で単独では機能しません。@CodeHater
ngIf
は新しいスコープを作成するので、ネストされた上記の例を見ると、同じ名前のモデルが親スコープに存在していてもngModel
、新しいdata
モデルが作成されます。ただし、ドット表記を使用すると、JSにスコープのプロトタイプチェーンを検索させます。したがって、現在のスコープで値が見つからない場合は、親スコープなどで値を探します。別のスコープを作成し、いくつかの他のディレクティブがありngInclude
、ngRepeat
。それが今明確であることを願っています。:)
興味深い点は、両方の優先順位の違いです。
私の知る限り、ng-ifディレクティブはすべてのAngularディレクティブの中で最も高い(最も高くないにしても)優先順位の1つです。つまり、他のすべての優先順位の低いディレクティブよりも先に最初に実行されます。最初に実行されるという事実は、要素が内部ディレクティブが処理される前に効果的に削除されることを意味します。または少なくとも:それは私がそれを作るものです。
私はこれを観察し、現在の顧客のために作成しているUIでこれを使用しました。UI全体はかなり重く詰め込まれ、その上にng-showとng-hideがありました。詳細には触れませんが、JSON構成を使用して管理できる汎用コンポーネントを作成したため、テンプレート内でいくつかの切り替えを行う必要がありました。ng-repeatが存在し、ng-repeat内には、ng-shows、ng-hides、さらにはng-switchsが多数存在するテーブルが表示されます。彼らは少なくとも50回の繰り返しをリストに表示したかったので、1500〜2000の指令が解決されることになります。コードを確認したところ、Javaバックエンド+前面のカスタムJSがデータを処理するのに約150ミリ秒かかり、Angularが表示するまでに2〜3秒かかりました。顧客は文句を言わなかったが、私はぞっとさせられた:-)
私の検索では、ng-ifディレクティブを偶然見つけました。さて、このUIを考案した時点では、利用可能なng-ifがなかったことを指摘するのが最善かもしれません。ng-showとng-hideにはブール値を返す関数が含まれていたため、これらすべてをng-ifで簡単に置き換えることができました。そうすることで、すべての内部ディレクティブが評価されなくなったように見えました。つまり、評価されているすべてのディレクティブの約3分の1に戻り、UIの読み込み時間が約500ミリ秒-1秒に高速化されました。(正確な秒を決定する方法はありません)
注:ディレクティブが評価されないという事実は、その下で何が起こっているかについての知識に基づいた推測です。
したがって、私の意見では、ページに要素を表示する必要がある場合(つまり、要素をチェックするためなど)、単に非表示にする場合は、ng-show / ng-hideを使用します。それ以外の場合はすべて、ng-ifを使用します。
ng-if
ディレクティブは、ページからコンテンツを削除し、ng-show/ng-hide
CSSの使用display
非表示コンテンツにプロパティを。
これは:first-child
、:last-child
スタイリングに疑似セレクターを使用する場合に役立ちます。
:first-child
し、:last-child
developer.mozilla.org/en-US/docs/Web/CSS/:first-child developer.mozilla.org/en-US/docs/Web/CSS/:last-child
ng-ifとng-showについて注意すべき重要な点の1つは、フォームコントロールを使用する場合ng-if
、要素をdomから完全に削除するため、フォームコントロールを使用するほうがよいということです。
で入力フィールドを作成しrequired="true"
、それng-show="false"
を非表示に設定すると、ユーザーがフォームを送信しようとするとChromeが次のエラーをスローするため、この違いは重要です。
An invalid form control with name='' is not focusable.
入力フィールドである理由は存在しますrequired
が、それが隠されているため、Chromeはそれにフォーカスできません。このエラーはスクリプトの実行を停止するため、文字通りコードを破壊する可能性があります。ので注意してください!
@Gajus Kuizinasと@CodeHaterは正しいです。ここでは例を挙げています。ng-ifの操作中に、割り当てられた値がfalseの場合、html要素全体がDOMから削除されます。割り当てられた値がtrueの場合、html要素はDOMに表示されます。また、スコープは親スコープとは異なります。ただし、ng-showの場合は、割り当てられた値に基づいて要素を表示および非表示にします。ただし、常にDOMに残ります。割り当てられた値に従って、可視性のみが変化します。
http://plnkr.co/edit/3G0V9ivUzzc8kpLb1OQn?p=preview
この例がスコープの理解に役立つことを願っています。ng-showおよびng-ifにfalse値を指定して、コンソールでDOMを確認してください。入力ボックスに値を入力して、違いを確認してください。
<!DOCTYPE html>
<input type="text" ng-model="data">
<div ng-show="true">
<br/>ng-show=true :: <br/><input type="text" ng-model="data">
</div>
<div ng-if="true">
<br/>ng-if=true :: <br/><input type="text" ng-model="data">
</div>
{{data}}
事実、そのng-if
ディレクティブはとは異なりng-show
、独自のスコープを作成し、興味深い実用的な違いをもたらします。
angular.module('app', []).controller('ctrl', function($scope){
$scope.delete = function(array, item){
array.splice(array.indexOf(item), 1);
}
})
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app='app' ng-controller='ctrl'>
<h4>ng-if:</h4>
<ul ng-init='arr1 = [1,2,3]'>
<li ng-repeat='x in arr1'>
{{show}}
<button ng-if='!show' ng-click='show=!show'>Delete {{show}}</button>
<button ng-if='show' ng-click='delete(arr1, x)'>Yes {{show}}</button>
<button ng-if='show' ng-click='show=!show'>No</button>
</li>
</ul>
<h4>ng-show:</h4>
<ul ng-init='arr2 = [1,2,3]'>
<li ng-repeat='x in arr2'>
{{show}}
<button ng-show='!show' ng-click='show=!show'>Delete {{show}}</button>
<button ng-show='show' ng-click='delete(arr2, x)'>Yes {{show}}</button>
<button ng-show='show' ng-click='show=!show'>No</button>
</li>
</ul>
<h4>ng-if with $parent:</h4>
<ul ng-init='arr3 = [1,2,3]'>
<li ng-repeat='item in arr3'>
{{show}}
<button ng-if='!show' ng-click='$parent.show=!$parent.show'>Delete {{$parent.show}}</button>
<button ng-if='show' ng-click='delete(arr3, x)'>Yes {{$parent.show}}</button>
<button ng-if='show' ng-click='$parent.show=!$parent.show'>No</button>
</li>
</ul>
</div>
最初のリストでは、inn / ownスコープのon-click
イベント、show
変数が変更されていますが、同じ名前の外部スコープの別の変数を監視しているため、ソリューションは機能しません。以下の場合には、我々だけ持って、それが動作する理由である変数を、。最初の試行を修正するには、を介して親/外部スコープから参照する必要があります。ng-if
ng-show
show
show
$parent.show
ng-if falseの場合、DOMから要素が削除されます。つまり、これらの要素に関連付けられているすべてのイベント、ディレクティブが失われます。たとえば、いずれかの子要素をng-clickすると、ng-ifがfalseと評価された場合、その要素はDOMから削除され、trueの場合は再作成されます。
ng-show / ng-hideはDOMから要素を削除しません。CSSスタイル(.ng-hide)を使用して要素を非表示/表示します。これにより、子にアタッチされたイベント、ディレクティブが失われることはありません。
ng-ifは子スコープを作成しますが、ng-show / ng-hideは作成しません。
ng-showとng-hideは逆の方法で機能します。ただし、ng-ifを使用したng-hideまたはng-showの違いは、ng-ifを使用する場合、要素はdomに作成されますが、ng-hide / ng-show要素を使用すると完全に非表示になります。
ng-show=true/ng-hide=false:
Element will be displayed
ng-show=false/ng-hide=true:
element will be hidden
ng-if =true
element will be created
ng-if= false
element will be created in the dom.
ちなみに、今私に起こったこと:ng-showはcssを介してコンテンツを非表示にします、しかし、それはdivのボタンであるはずの奇妙なグリッチをもたらしました。
下部に2つのボタンが付いたカードがあり、実際の状態に応じて、新しいエントリのある3番目の編集ボタンと交換されます。ng-show = falseを使用して左側のファイル(ファイルの最初に存在)を非表示にすると、次のボタンがカードの外側の右側の境界線で終了することがありました。ng-ifは、コードをまったく含めないことで修正します。(ng-showの代わりにng-ifを使用していくつかの隠された驚きがあるかどうか、ここで確認してください)
ng-ifとng-showの興味深い違いの1つは次のとおりです。
セキュリティ
ng-ifブロックに存在するDOM要素は、その値がfalseの場合はレンダリングされません
ng-showの場合と同様に、ユーザーはInspect Element Windowを開いてその値をTRUEに設定できます。
そして、おっと、非表示にしようとしたコンテンツ全体が表示されます。これはセキュリティ違反です。:)
ng-if
で追加されたモデルでHTML要素自体を削除すると、ng-model
もう存在しなくなります。