2017-08-06 1 views
2

Ich benutze ein einfaches Captcha in meinem Popup-Dialog mit bPopup Plugin.Wie man einfaches Captcha in Direktive neu lädt?

Sie können den Captcha-Code auf diese jsfiddle verweisen: https://jsfiddle.net/Mazzu/hspxaeqa/

HTML:

<span id="popup-button-email">Click Here!</span> 

<div id="popup-second"> <a class="b-close">x<a/> 
     <simple-captcha valid="captchaValid"></simple-captcha> 
</div> 

JS:

app.directive('simpleCaptcha', function() { 
    return { 
     restrict: 'E', 
     scope: { valid: '=' }, 
     template: '<input ng-model="a.value" ng-show="a.input" style="width:2em; text-align: center;"><span ng-hide="a.input">{{a.value}}</span>&nbsp;{{operation}}&nbsp;<input ng-model="b.value" ng-show="b.input" style="width:2em; text-align: center;"><span ng-hide="b.input">{{b.value}}</span>&nbsp;=&nbsp;{{result}}', 
     controller: function($scope) { 

      var show = Math.random() > 0.5; 

      var value = function(max){ 
       return Math.floor(max * Math.random()); 
      }; 

      var int = function(str){ 
       return parseInt(str, 10); 
      }; 

      $scope.a = { 
       value: show? undefined : 1 + value(4), 
       input: show 
      }; 
      $scope.b = { 
       value: !show? undefined : 1 + value(4), 
       input: !show 
      }; 
      $scope.operation = '+'; 

      $scope.result = 5 + value(5); 

      var a = $scope.a; 
      var b = $scope.b; 
      var result = $scope.result; 

      var checkValidity = function(){ 
       if (a.value && b.value) { 
        var calc = int(a.value) + int(b.value); 
        $scope.valid = calc == result; 
       } else { 
        $scope.valid = false; 
       } 
       $scope.$apply(); // needed to solve 2 cycle delay problem; 
      }; 


      $scope.$watch('a.value', function(){  
       checkValidity(); 
      }); 

      $scope.$watch('b.value', function(){  
       checkValidity(); 
      }); 
     } 
    }; 
}); 

: Pop-up

$('#popup-button-email').bind('click', function(e) { 
    // Prevents the default action to be triggered. 
    e.preventDefault(); 

    // Triggering bPopup when click event is fired 
    $('#popup-second').bPopup(); 
}); 

Alle sieht gut aus, außer o ne Sache.

Nachdem ich das Pop-up geschlossen habe und ich ein weiteres Popup öffne, hat es das Captcha nicht neu geladen, was sehr merkwürdig ist.

Irgendwelche Ideen, wie man das Captcha neu lädt, nachdem ich das pop-up schließe?

Danke

+0

Alles, was ich sehe, ist eine Arbeitsauswertung in der Probe. Warum mischst du jQuery und eckig? Das ist wahrscheinlich ein Teil des Grundes. Nicht sicher, was du meinst, wenn du neu lädst. Der Controller wird nicht einfach wieder laufen. Sie sollten wahrscheinlich eine Funktion 'loadCaptcha()' haben und diese einmal aufrufen, wenn der Controller geladen wird, und erneut, wenn das Popup geschlossen wird. – Brian

Antwort

0

Sie müssen nur ein oder zwei Dinge aktualisieren. In checkvalidity Funktion der Direktive $scope.$apply() verursacht $ Digest-Zyklus zu laufen, wenn es bereits im Gange ist, so dass es brechen, um zu vermeiden, dass Sie checkvalidity Funktion im Bereich Variable der Direktive Controller & diese explizite Aufruf von $ apply entfernen können. Auch, wie $('#popup-second').bPopup() Aufruf nicht tatsächlich rendern die Direktive, so dass es immer zuerst geladene Ergebnisse der Direktive zeigt. Also, was Sie tun können, ist ng-wenn auf diesem direktiven Element in Ihrer Sicht & schalten Sie es auf onClose & onOpen Ereignisse von bPopup(). So können Sie Ihre Vorlage sein:

<div id="popup-second" style="display: none"> 
    <div> From Controller : {{mymodel.captchaValid}} 
    </div> 
    <div ng-if="show"> 
     <simple-captcha valid="mymodel.captchaValid"></simple-captcha> 
    </div> 
</div> 

aktualisieren CheckValidity Funktion innerhalb Richtlinie als:

$scope.checkValidity = function() { 
    if (a.value && b.value) { 
     var calc = int(a.value) + int(b.value); 
     $scope.valid = calc == result; 
    } else { 
     $scope.valid = false; 
    } 
}; 

$scope.$watch('a.value', function(){  
    $scope.checkValidity(); 
}); 

$scope.$watch('b.value', function(){  
    $scope.checkValidity(); 
}); 

Und in der Steuerung der Ansicht Call bPopup als:

$('#popup-button-email').bind('click', function(e) { 
    // Prevents the default action to be triggered. 
    e.preventDefault(); 

    // Triggering bPopup when click event is fired 
    $('#popup-second').bPopup({ 
     onOpen: function() { 
     $scope.show = true; 
     $scope.$digest(); 
     }, 
     onClose: function() { 
     $scope.show = false; 
     $scope.$digest(); 
     } 
    }); 
}); 

So auf diese Weise die Richtlinie wird jedes Mal neu erstellt, wenn Sie es auslösen. Es gibt also die erwarteten Ergebnisse & Dank der isolierten Bereich können Sie es mehrmals auf der gleichen Ansicht oder andere Ansicht der App wiederverwenden.

Working plunker

Verwandte Themen