angular.js içindeki satır içi koşullar


192

Koşullu olarak ng-show vb kullanmaktan başka içeriği görüntülemek için bir yol olup olmadığını merak ediyordum. Örneğin backbone.js'de ben gibi bir şablonda satır içi içerik ile bir şey yapabilirdi:

<% if (myVar === "two") { %> show this<% } %>

ancak açısal olarak, html etiketlerine sarılmış şeyleri göstermek ve gizlemekle sınırlı görünüyorum

<p ng-hide="true">I'm hidden</p>
<p ng-show="true">I'm shown</p>

İçeriği html etiketlerine sarmak yerine yalnızca {{}} kullanarak satır içi içeriği açısal olarak koşullu olarak göstermek ve gizlemek için açısal olarak önerilen yol nedir?


6
lütfen benim cevap kabul etmeyin bir şans 2Toad's bir şans olsun.
Ben Lesh

Yanıtlar:


139

DÜZENLEME: 2Aşağıdaki cevabı aradığınız şey! O şeyi oyla

Açısal <= 1.1.4 kullanıyorsanız, bu cevap şunları yapacaktır:

Bunun için bir cevap daha. Ayrı bir cevap gönderiyorum, çünkü bir çözüm için olası çözümlerin bir listesinden çok "kesin" bir girişimdir:

İşte "hemen if" (aka iif) yapacak bir filtre:

app.filter('iif', function () {
   return function(input, trueValue, falseValue) {
        return input ? trueValue : falseValue;
   };
});

ve şu şekilde kullanılabilir:

{{foo == "bar" | iif : "it's true" : "no, it's not"}}

Teşekkür ederim, ben de bunun için gidiyordum. Ancak ben bir html etiketi değerlerinden birine koymaya çalışırsanız kırdığı dikkat edin: {{thing.second == "iki" | iif: "<ul class = 'two-class'>": "<ul>"}} Bunu açısal olarak yapmanın daha iyi yolları olabileceğini, ancak "<" ve ">" böylece etiketler dizenin bir parçası olarak çıktı olabilir?
user1469779

1
ngBind HTML çıktısına izin vermiyor, ng-bind-html-unsafe
Ben Lesh

Açısal belgelerdeki ng-binf-html-güvensiz örneği, etiketi bir etiket içinde kullanır; örneğin, <ANY ng-bind-html-unsafe = "{expression}">. satır içi yapmaya çalıştığım şeyi yapmak mümkün olmayabilir.
user1469779

1
IIF "Inline If" kısaltmasıdır. Farklı programlama dillerinde yaygındır ... sadece?: Satır içi ifs kadar yaygın değildir. ;)
Ben Lesh

18
@BenLesh Şimdi başka seçenekler, iyi iş var cevabınızı düzenlemek için büyük sahne.
Nick Coad

725

Üçlü operatörler için açısal 1.1.5 ek destek:

{{myVar === "two" ? "it's true" : "it's false"}}

14
En çok oy alan bu cevap cevapların en üstünde görünmelidir ... açık ara en doğru
Code Whisperer

3
user1469779 bu cevabı kabul etmeyi düşünün, çünkü bu bir süre için istediğinizi elde etmenin önerilen yolu
Filip Kis

13
@ 2Şekil, cevabım eskiydi. Bu şimdi doğru cevap, kullanıcı şimdi "kabul" için geri dönüp dönmeyeceğini bilmiyorum, ama cevabımı bu şekilde açıklama ekledim. Yazılım geliştirmenin değişen yüzü böyledir.
Ben Lesh

2
Teşekkürler. myVarYalnızca yanlışsa değerini nasıl gösterebilirim ? (yani ifadedeki değişkenleri nasıl iç içe yerleştirebilirim?) Denedim {{myVar === "two" ? "it's true" : {{myVar}}}}ama çalışmıyor.
Josh

6
@Josh myVarözelliğin ek kıvırcık parantez içine sarılmasına gerek yok, zaten bir ifadenin içinde. Deneyin{{myVar === "two" ? "it's true" : myVar}}
2Toad

60

Bu kediyi yüzmek için binlerce yol. {{}} Arasında özel olarak sorduğunuzun farkındayım, ancak buraya gelen diğerleri için, diğer seçeneklerden bazılarını göstermeye değer olduğunu düşünüyorum.

$ kapsamınızda (IMO, çoğu senaryoda en iyi bahsiniz):

  app.controller('MyCtrl', function($scope) {
      $scope.foo = 1;

      $scope.showSomething = function(input) {
           return input == 1 ? 'Foo' : 'Bar';
      };
   });

 <span>{{showSomething(foo)}}</span>

ng-show ve ng-hide tabii ki:

 <span ng-show="foo == 1">Foo</span><span ng-hide="foo == 1">Bar</span>

ngSwitch

 <div ng-switch on="foo">
   <span ng-switch-when="1">Foo</span>
   <span ng-switch-when="2">Bar</span>
   <span ng-switch-default>What?</span>
 </div>

Bertrand'ın önerdiği gibi özel bir filtre. (aynı şeyi tekrar tekrar yapmak zorundaysanız, bu en iyi seçimdir)

app.filter('myFilter', function() {
   return function(input) {
     return input == 1 ? 'Foo' : 'Bar';
   }
}

{{foo | myFilter}}

Veya özel bir direktif:

app.directive('myDirective', function() {
   return {
     restrict: 'E',
     replace: true,
     link: function(scope, elem, attrs) {
       scope.$watch(attrs.value, function(v) {
          elem.text(v == 1 ? 'Foo': 'Bar');
       });
     }
   };
});


<my-directive value="foo"></my-directive>

Şahsen, çoğu durumda kapsamımdaki bir işlevle giderdim, işaretlemeyi oldukça temiz tutar ve uygulanması hızlı ve kolaydır. Tabii, aynı şeyi tekrar tekrar yapacağınız sürece, bu durumda Bertrand'ın önerisiyle gidip koşullara bağlı olarak bir filtre veya muhtemelen bir yönerge oluşturacağım.

Her zaman olduğu gibi , en önemli şey çözümünüzün bakımı kolay ve umarım test edilebilir olmasıdır. Ve bu tamamen sizin özel durumunuza bağlı olacaktır.


18

Ng sınıfı kullanılamaz (örneğin SVG stil) zaman koşullu olarak sınıf attr ayarlamak için aşağıdaki kullanıyorum:

ng-attr-class="{{someBoolean && 'class-when-true' || 'class-when-false' }}"

Aynı yaklaşım diğer özellik türleri için de geçerli olmalıdır.

(Ng-attr- kullanmak için en son dengesiz açısal olmanız gerektiğini düşünüyorum, şu anda 1.1.4'deyim)

AngularJS + SVG ile çalışma hakkında bu ve ilgili konular hakkında konuşan bir makale yayınladım. http://www.codeproject.com/Articles/709340/Implementing-a-Flowchart-with-SVG-and-AngularJS


15

Değişken bir içeriği kontrol etmek ve varsayılan bir metne sahip olmak için şunları kullanabilirsiniz:

<span>{{myVar || 'Text'}}</span>

1
teşekkür ederim! Bunu deniyordum ama dize çevresindeki tırnakları
özlüyorum

Her ne sebeple olursa olsun, bu sözdizimi tek seferlik bağlamalar kullanılarak çalışmaz. {{:: myVar || 'Metin'}} çalışmaz. ::
aoakeson

3

Eğer seni iyi anladıysam, bunu yapmanın iki yolu olduğunu düşünüyorum.

İlk olarak ngSwitch'i deneyebilirsiniz ve ikinci olası yol kendi filtrenizi oluşturmak olacaktır . Muhtemelen ngSwitch doğru yaklaşımdır, ancak satır içi içeriği gizlemek veya göstermek istiyorsanız, yalnızca {{}} filtre kullanarak gitmek için yoldur.

İşte örnek olarak basit bir filtreye sahip bir keman .

<div ng-app="exapleOfFilter">
  <div ng-controller="Ctrl">
    <input ng-model="greeting" type="greeting">
      <br><br>
      <h1>{{greeting|isHello}}</h1>
  </div>
</div>

angular.module('exapleOfFilter', []).
  filter('isHello', function() {
    return function(input) {
      // conditional you want to apply
      if (input === 'hello') {
        return input;
      }
      return '';
    }
  });

function Ctrl($scope) {
  $scope.greeting = 'hello';
}

3

Açısal UI kütüphanesi, şablon /

Örnek: 1.1.4'e kadar Açısal UI'de destek

<div ui-if="array.length>0"></div>

ng-1.1.4'ten sonraki tüm açısal versiyonlarda mevcutsa

<div ng-if="array.length>0"></div>

dizi değişkeninde herhangi bir veri varsa, yalnızca div görüntülenir


ui-ifen azından en son sürüm açısal-ui kaldırıldı ama açısal 1.1.5 beri ng-if( bu yorumdan ) var
Dave Everitt

2

Yani Açısal 1.5.1 ile (diğer MEAN yığın bağımlılıklarına mevcut uygulama bağımlılığı vardı, neden şu anda 1.6.4 kullanmıyorum)

Bu benim için OP'nin söylediği gibi çalışıyor {{myVar === "two" ? "it's true" : "it's false"}}

{{vm.StateName === "AA" ? "ALL" : vm.StateName}}

2

değer "0" olduğunda "Hiçbiri" ni görüntülemek istiyorsanız, şu şekilde kullanabilirsiniz:

<span> {{ $scope.amount === "0" ?  $scope.amount : "None" }} </span>

veya açısal j'lerde gerçek yanlış

<span> {{ $scope.amount === "0" ?  "False" : "True" }} </span>

1

Egzotik durumlarda bile çalışır:

<br ng-show="myCondition == true" />

0

Karışımı benimkine atacağım:

https://gist.github.com/btm1/6802312

bu, if ifadesini bir kez değerlendirir ve izleme dinleyicisi eklemez, ancak bekle-for = "somedata.prop" adlı set-if öğesine sahip öğeye ek bir özellik ekleyebilirsiniz ve bu verilerin veya özelliğin daha önce ayarlanmasını bekleyecektir if ifadesini bir kez değerlendirmek. bir XHR isteğinden veri bekliyorsanız bu ek özellik çok kullanışlı olabilir.

angular.module('setIf',[]).directive('setIf',function () {
    return {
      transclude: 'element',
      priority: 1000,
      terminal: true,
      restrict: 'A',
      compile: function (element, attr, linker) {
        return function (scope, iterStartElement, attr) {
          if(attr.waitFor) {
            var wait = scope.$watch(attr.waitFor,function(nv,ov){
              if(nv) {
                build();
                wait();
              }
            });
          } else {
            build();
          }

          function build() {
            iterStartElement[0].doNotMove = true;
            var expression = attr.setIf;
            var value = scope.$eval(expression);
            if (value) {
              linker(scope, function (clone) {
                iterStartElement.after(clone);
                clone.removeAttr('set-if');
                clone.removeAttr('wait-for');
              });
            }
          }
        };
      }
    };
  });
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.