How to activate ng-submit from a timer call-back? - angularjs

I have a timer that would re-submit the page at intervals. Is there an angular way to do that?
Right now I was just submitting the form inside a script:
<script type="text/javascript" defer="defer">
window.setTimeout( function () {
document.getElementById( "srchForm" ).submit();
}, 300000 ); //5 min
</script>
<form id="srchForm" ng-controller="OutageViewController" ng-submit="loadData(0)">
<p id="div_srchForm"> ....</p>
<button id="btnReload" type="submit" >Submit</button>
</form>
but it would give me 404 error status:
404 - File or directory not found.
The resource you are looking for might have been removed, had its name changed, or is temporarily unavailable

Use $interval service to schedule a function for repeated execution with a time interval in between.
Example that used the $interval service to schedule a function call every 3 seconds:
var app = angular.module('MyApp', []);
app.controller('MainCtrl', function($scope, $interval) {
$scope.loadData = function() {
console.log("loadData - Interval occurred");
};
$interval(function() {
$scope.loadData();
}, 3000);
});
<form id="formX" ng-controller="MainCtrl" ng-submit="loadData(0)">
<p id="div_srchForm"> ....</p>
<button id="btnReload" type="submit">Submit</button>
</form>
https://plnkr.co/edit/yqMW9ZENoqZwfDtqlsTy

I would rather ask why you are trying to simulate a button click in the first place. As others have hinted at, browser automation as a user experience is typically a poor choice and reflects poor organization in your software design. I would recommend using the $timeout already available in Angular to do this from the controller instead. Not only does this put your front end logic where it belongs,in the controller, but also gives you a clean teardown mechanism so your timer doesn't continue I run if the controller isn't active (and prevents you from writing another hack to mitigate that).

I have found a non-Angular way to work around to get to the ng-submit handler:
Looks like I cannot call form.submit in the callback. When I did that, they can't "see" ng-submit and it lost me where the call has taken me when it complained not finding "resources" which is the page itself! My work-around to connect to the ng-submit is,
Now instead of doing form.submit in the callback, I click the submit button which is just primitive js but it did the job!
<script type="text/javascript" defer="defer">
window.setTimeout( function () {
document.getElementById( "btnReload" ).click();
//window.location.reload();
}, 300000 ); //5 min
</script>
The button activated ng-submit because of the way the scope of submit was set up. Just don't ask me why clicking the button is working but form-submitting is not working!
After all, I still want to know the Angular Way to do it, not my primitive js !!

Related

how does binding to a service method work?

In this first example, the the view is updated everytime the return value of the method sessionStatus() of userService changes.
but If a change the sessionStatus method like in the second example :
sessionStatus: function(){
return Date.now();
},
it no longer refreshes "live" in the view. I would expect to see the date in milliseconds progressing in the view.
Is it because the second example, the value returned by the sessionStatus method is changing to fast ? Why isn't it updating the view ?
The value is not updating because there is no AngularJS event to cause a digest cycle:
Add a button that has an ng-click and the value will update everytime it is clicked:
<body ng-app="myServiceModule">
<div id="simple" ng-controller="MyController">
<p>I would expect the number bellow to be ticking</p>
<p>Session Status: {{sessionStatus()}}</p>
</div>
<button ng-click="">Update</button>
</body>
By clicking on the Update button, an AngularJS digest cycle gets initiated and the session status updates.
The DEMO on PLNKR.
Or use the $interval service to initiate a repeating digest cycle:
angular.
module('myServiceModule', []).
controller('MyController', function ($scope, $interval, userService) {
$scope.sessionStatus = function(){
return userService.sessionStatus();
};
$interval(null, 250);
})
In this example, the $interval statement starts a digest cycle every 250 milliseconds.
The DEMO on PLNKR

how to pass form action on button click as well as perform some functionality on that button click?

i want to perform 2 action on button click
1) is perform save operation and on that success
2)goto paypal
<form role="form" id="checkoutform" name="checkoutform" novalidate="novalidate" ng-submit="saveClick()" action="https://www.sandbox.paypal.com/cgi-bin/webscr">
...
...
..
<button type="submit" id="purchase" class="btn btn-primary">Purchase</button>
</form>
using angular js.
You answered your own question for #1 I believe.
1) is perform save operation and on that success
The ng-click="saveClick()" directive will fire the saveClick() function in your controller.
There you can perform your save operation.
If you don't have your app or controller setup visit AngularJS docs here. Angular Getting Started
2)goto paypal
For this, checkout out angular injected service $location. You can do something like $location.path("https://www.paypal.com")
Here is a link
If you need to hit the link from your controller rather than send the user to the page you'll want to use angulars $http injected service.
Here
when you have 2 form in 1 html file then if you want to call another form (2nd) on click of first form button then ...
this is the best solution using angularjs
i created on function in .js file
$scope.load = function () {
document.getElementById("paypalform").submit();
}
and call it in another function like save()
my first form have 1 button and its call save after that on success of save function i call this one...
$timeout(function () { $scope.load(); }, 1000, true);
this function calls another form(2nd) which name like paypalform.
and its working..

How do I get my changes to persist in Angular using 2-way Data Binding with an onDrag callback?

I am trying to update a span's text after a call back function in Angular.
Here is my HTML:
<div ng-controller="onDragController">
<div id="draggableArea">
<div id="rectangle1" data-drag="true" jqyoui-draggable="{onDrag: 'dragCallback'}" data-jqyoui-options="{containment: '#draggableArea'}"></div>
</div>
<div>
<span ng-model="rectangleOne">{{rectangleOne.leftOffset}}</span>
</div>
</div>
And my controller is:
var App = angular.module('drag-and-drop', ['ngDragDrop', 'ui.bootstrap']);
App.controller('onDragController', function($scope) {
$scope.rectangleOne = {};
$scope.rectangleOne.leftOffset = 'ASDF';
$scope.dragCallback = function (event, ui) {
$scope.rectangleOne = {leftOffset: '12345'};
};
});
If I toss an alert in my callback function then I am seeing that the leftOffSet is updated, but on my HTML page the {{rectangleOne.leftOffset}} is staying the same.
What am I missing here...?
Use $apply in your dragCallback as follows:
$scope.dragCallback = function(event, ui) {
$scope.$apply(function() {
$scope.rectangleOne = {
leftOffset: '12345'
};
});
};
This will update your leftOffset in the scope. Here is a Plunker.
It might be helpful to better understand how Angular does two-way data binding. This blog post on how apply works, and why one would be motivated to use it, is pretty good.
In summary, for your changes to $scope.rectangleOne:
You can call $scope.$digest() every time you make a simple change like this. You need to do this so Angular knows to check if your bound data got updated.
Alternatively, you can use $scope.$apply, make the changes to $scope.rectangleOne inside a callback to $apply. It's doing the same thing, $apply ends up calling $digest() indirectly.
In code:
$scope.$apply(function() {
$scope.rectangleOne.leftOffset = '12345';
});
Hope that helps solve your problem, and add a bit of understanding to what's happening behind the scenes!

How does AngularJS respond to a form value being updated in Javascript?

I don't use Angular regularly, but I understand that one of the key features is that when data is updated on a form element, it is automatically updated in the model.
If you are instead using a library like jQuery, you must manually attach an event to the form input that updates the model when it is changed, as in $('#myInput').on('change', updateModel);
Although the above handler will be fired when myInput is changed by the user, it will not be fired if myInput is changed by Javascript code such as $('#myInput').val('hello world');
My question is, how does Angular know when a form input is changed in Javascript code?
Angular applies a scope digest every time it's needed (by an Angular function) during which it checks the states of all the scope variables, including the models used, of course.
If you modify some of those variables manually, using JavaScript, jQuery, etc... Angular will not know that the changes have occured and you need to tell it so either by doing $scope.$apply() or by wrapping the code block in a $timeout callback (these are the most commonly used methods).
If you don't do it manually, you'd have to wait for some (if any) other Angular event to trigger the digest cycle, which is never good.
See this example, note how nothing happens when you just update the value, but you need to do it manually (ng-click does it) in order for DOM to update:
angular.module('app', [])
.controller('Ctrl', function($scope){
$scope.ourValue = 'Initial Value';
window.exposedFunc = function(v, digest) {
$scope.ourValue = v;
if (digest) {
$scope.$apply();
}
}
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="Ctrl">
<button onclick="exposedFunc('First Button Value')">Update Value - No Digest</button>
<button onclick="exposedFunc('Second Button Value', true)">Update Value - Force Digest</button>
<button ng-click="">Force Digest only</button>
<p>{{ourValue}}</p>
</div>
Here's a super simple example of binding using keyup event. It should be enough to get you started on your projects:
var res = document.getElementById('r');
function handleChange(v) {
res.textContent = v;
}
<input onkeyup="handleChange(this.value)" type="text" value="Initial value" />
<p id="r">No binding yet</p>

Simple timer by angulars js did not work

I try to set up a timer by angular.js.
Could someone tell me why the method2 won`t work?
I had set up an alert to make sure the function had been triggered.
Many thanks.
HTML
<div ng-controller="MyController">
<h5>{{ clock }}</h5>
</div>
JS
function MyController($scope) {
alert("start point check");
var updateClock = function() {
$scope.clock = new Date();
};
//method1.
setInterval(function() {$scope.$apply(updateClock);}, 1000);
//method2.
//setInterval(updateClock, 1000);
updateClock();
};
Actually, you should be using $timeout instead of setInterval.
The reason second option does't work is that Angular $digest doesn't identify the changes made via setInterval. It's outside of Angular, hence you need to do a $scope.$apply.
check this link for better understanding of $apply.

Resources