Angular only update input field when not having focus - javascript

I have an input field which is for both setting and readback. I would like to have the following behavior:
No focus: update the field with readback
Focus: no update, if enter is pressed call send with the value written in the field.
I have a mwe which is a start but does update when focused.
<!DOCTYPE html>
<html lang="en">
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.6.5/angular.js"></script>
<script>
angular.module('App', []).controller('world', function ($scope) {
$scope.value1 = 0;
$scope.value2 = 0;
$scope.send = function(value) {
alert(value);
}
let readback = function() {
$scope.value1 += 1;
$scope.value2 += 1;
$scope.$apply();
setTimeout(readback, 100);
};
setTimeout(readback, 1);
});
</script>
</head>
<body ng-app="App" ng-controller="world">
<input type="text" ng-model="value1" ng-keyup="$event.keyCode == 13 && send(value1)" />
<input type="text" ng-model="value2" ng-keyup="$event.keyCode == 13 && send(value2)" />
</body>
Edit: Sorry I was a bit unclear and cut down my mwe too much. I have about ten such input fields. The unfocused fields should still update while only the one which is selected does not.

you can detect ng-focus and ng-blur, using separate controller instances for each input:
<!DOCTYPE html>
<html lang="en">
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.6.5/angular.js">
</script>
<script>
angular.module('App', []).controller('world', function ($scope) {
let isFocus = false;
$scope.value = 0;
$scope.send = () => alert($scope.value);
$scope.focus = () => isFocus = true;
$scope.blur = () => isFocus = false;
let readback = function() {
if (!isFocus) {
$scope.value += 1;
$scope.$apply();
}
setTimeout(readback, 100);
};
setTimeout(readback, 1);
});
</script>
</head>
<body ng-app="App">
<input type="text"
ng-controller="world"
ng-model="value"
ng-keyup="$event.keyCode == 13 && send()"
ng-focus="focus()"
ng-blur="blur()" />
<input type="text"
ng-controller="world"
ng-model="value"
ng-keyup="$event.keyCode == 13 && send()"
ng-focus="focus()"
ng-blur="blur()" />
</body>

Related

Validation of a Simple Form

In process of learning JS. Trying to learn how to loop through an entire form, and have errors pointed out.
This is a hodgepodge that I cobbled together from various tutorials online.
Clearly it's not working.
What I am trying to do is to get the forms' entire collection of its elements, and loop through it, and anything that's blank, to have its error message printed somewhere on the same screen, be it above the form or underneath the textboxes itself.
This is what I have so far. Any help in getting this to work, or at least the concept of what I outlined? Simple and bite-size explanations if possible would be appreciated.
<!DOCTYPE HTML>
<html>
<head>
<meta charset="utf-8" />
</head>
<body>
<form method="post" action="" id="myForm">
<div id="validation"></div>
<p><label>Name<br><input type="text" name="Name"></label></p>
<p><label>Email<br><input type="text" name="Email"></label></p>
<p><input type="submit" value="Submit"></p>
</form>
<script>
var formsCollection = document.forms[0];
for (var i = 0; i < formsCollection.elements.length; i++) {
if (formsCollection.elements.value.length == 0) {
form.elements.input.border = "1px solid red";
form.Name.style.backgroundColor = "#FFCCCC";
}
return true;
}
document.getElementById("myForm").onsubmit = function () {
return Validate(this);
};
</script>
</body>
</html>
EDIT
<script>
function Validate() {
var formsCollection = document.forms[0];
for (var i = 0; i < formsCollection.elements.length; i++) {
if (formsCollection.elements[i].value.length == 0) {
form.elements.input.border = "1px solid red";
form.Name.style.backgroundColor = "#FFCCCC";
}
return true;
}
document.getElementById("myForm").onsubmit = function () {
return Validate(this);
};
}
</script>
Full ans:
<!DOCTYPE HTML>
<html>
<head>
<meta charset="utf-8" />
</head>
<body>
<form method="post" action="" id="myForm">
<div id="validation"></div>
<p><label>Name<br><input type="text" name="Name"></label></p>
<p><label>Email<br><input type="text" name="Email"></label></p>
<p><input type="submit" value="Submit"></p>
</form>
<script>
document.forms[0].onsubmit= function() {
var form = document.forms[0];
for (var i = 0; i < form.elements.length; i++) {
if (form.elements[i].value.length == 0) {
console.log(form.elements[i]);
form.elements[i].border = "1px solid red";
form.elements[i].style.backgroundColor = "#FFCCCC";
return false;
}
}
}
</script>
</body>
</html>
Several problems.
There seems to be no i in your for loop usage.
Try if (formsCollection.elements.value.length == 0) {
to if (formsCollection.elements[i].value.length == 0) {
Where is your Validate function?
Wrap var formsCollection ... END_OF_FOR_LOOP with function Validate(){ and }

Unable to trigger submit in angularJS from a single button

Using ng-submit I have a form submission callback namely submitFN. Have 2 buttons:
Fund my startup!
Reset
My desirable output is on clicking the reset button, the input field gets 0. And on clicking "Fund my startUp" it shows an alert. How to attain this?
Problem:
Both the buttons are triggering the submitFN. Unable to reset.
Code:
<!DOCTYPE html>
<html>
<head>
<title></title>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.js">
</script>
<script>
var mainApp = angular.module("mainApp", []);
mainApp.controller('startUpController', function($scope) {
$scope.funding = {
startingEstimate: 0
};
$scope.calculate = function () {
$scope.funding.needed = $scope.funding.startingEstimate * 10;
};
$scope.submitFN = function () {
window.alert('Go and find more customers.')
}
$scope.resetFN = function () {
$scope.startingEstimate = 0;
}
});
</script>
</head>
<body>
<div ng-app='mainApp'>
<form ng-submit="submitFN()" ng-controller="startUpController">
Starting: <input type="text" ng-change="calculate()" ng-model="funding.startingEstimate"/>
Recommended: {{funding.needed}}
<button>Fund my startup!</button>
<button ng-click="resetFN()">Reset</button>
</form>
</div>
</body>
</html>
I am entirely novice in angularJS and any help is highly appreciable. Thanks in advance.
UPDATE
One of code I tried:
<!DOCTYPE html>
<html>
<head>
<title></title>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.js">
</script>
<script>
var mainApp = angular.module("mainApp", []);
mainApp.controller('startUpController', function($scope) {
$scope.funding = {
startingEstimate: 0
};
$scope.calculate = function () {
$scope.funding.needed = $scope.funding.startingEstimate * 10;
};
$scope.submitFN = function () {
window.alert('Go and find more customers.')
}
$scope.resetFN = function () {
$scope.startingEstimate = 0;
}
});
</script>
</head>
<body>
<div ng-app='mainApp'>
<form ng-submit="submitFN()" ng-controller="startUpController">
Starting: <input type="text" ng-change="calculate()" ng-model="funding.startingEstimate"/>
Recommended: {{funding.needed}}
<button>Fund my startup!</button>
<button type = "button" ng-click="resetFN()">Reset</button>
</form>
</div>
</body>
</html>
By default the button type is submit, so you the 2nd button also has button type submit. If you don't want to submit a form on that button, you should explicitly make that button type as a button
type="button"
Also you had mistake in resetFN code, It should be modify a value which is assigned to ng-model
$scope.resetFN = function () {
$scope.funding.startingEstimate = 0;
}
corrected code below:
<!DOCTYPE html>
<html>
<head>
<title></title>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.js">
</script>
<script>
var mainApp = angular.module("mainApp", []);
mainApp.controller('startUpController', function($scope) {
$scope.funding = {
startingEstimate: 0
};
$scope.calculate = function () {
$scope.funding.needed = $scope.funding.startingEstimate * 10;
};
$scope.submitFN = function () {
window.alert('Go and find more customers.')
}
$scope.resetFN = function () {
$scope.funding.startingEstimate = 0;
}
});
</script>
</head>
<body>
<div ng-app='mainApp'>
<form ng-submit="submitFN()" ng-controller="startUpController">
Starting: <input type="text" ng-change="calculate()" ng-model="funding.startingEstimate"/>
Recommended: {{funding.needed}}
<button>Fund my startup!</button>
<button type="button" ng-click="resetFN()">Reset</button>
</form>
</div>
</body>
</html>
You miss funding
$scope.resetFN = function () {
$scope.funding.startingEstimate = 0;
}

Show only clicked element values from multiple ng-click events angularjs

i have 10 more ng-click events, but i want to show only clicked element value where i have to change, but i updated in code there was so many true or false duplicates i have to write, pls help me that have to show only clicked ng-show values without using 'true or false' booleen functions in each click event.
var app = angular.module('myapp', ['ngSanitize']);
app.controller('AddCtrl', function ($scope, $compile) {
$scope.field = {single: 'untitled',single2:'default',single3:'enter'};
$scope.addName1 = function (index) {
var name1html = '<fieldset id="name1" ng-click="selectName1($index)"><label ng-bind-html="field.single"></label><input type="text" placeholder="Enter name"><button ng-click="removeName1($index)">-</button></fieldset>';
var name1 = $compile(name1html)($scope);
angular.element(document.getElementById('drop')).append(name1);
};
$scope.removeName1 = function (index) {
var myEl = angular.element(document.querySelector('#name1'));
myEl.remove();
};
$scope.selectName1 = function (index) {
$scope.showName1 = true;
$scope.showName2 = false;
$scope.showName3 = false;
};
$scope.addName2 = function (index) {
var name2html = '<fieldset id="name2" ng-click="selectName2($index)"><label ng-bind-html="field.single2"></label><input type="text" placeholder="Enter name"><button ng-click="removeName2($index)">-</button></fieldset>';
var name2 = $compile(name2html)($scope);
angular.element(document.getElementById('drop')).append(name2);
};
$scope.removeName2 = function (index) {
var myEl = angular.element(document.querySelector('#name2'));
myEl.remove();
};
$scope.selectName2 = function (index) {
$scope.showName2 = true;
$scope.showName1 = false;
$scope.showName3 = false;
};
$scope.addName3 = function (index) {
var name3html = '<fieldset id="name3" ng-click="selectName3($index)"><label ng-bind-html="field.single3"></label><input type="text" placeholder="Enter name"><button ng-click="removeName3($index)">-</button></fieldset>';
var name3 = $compile(name3html)($scope);
angular.element(document.getElementById('drop')).append(name3);
};
$scope.removeName3 = function (index) {
var myEl = angular.element(document.querySelector('#name3'));
myEl.remove();
};
$scope.selectName3 = function (index) {
$scope.showName3 = true;
$scope.showName1 = false;
$scope.showName2 = false;
};
});
<!DOCTYPE html>
<html ng-app="myapp">
<head>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0-beta.2/angular.min.js"></script>
<script src="https://code.angularjs.org/1.5.0-rc.0/angular-sanitize.min.js"></script>
</head>
<body ng-controller="AddCtrl">
<div id="drop"></div>
<button ng-click="addName1($index)">Name1</button>
<button ng-click="addName2($index)">Name2</button>
<button ng-click="addName3($index)">Name3</button>
<form ng-show="showName1">
<div class="form-group">
<label>Field Label(?)</label>
<br/>
<input ng-model="field.single">
</div>
</form>
<form ng-show="showName2">
<div class="form-group">
<label>Field Label(?)</label>
<br/>
<input ng-model="field.single2">
</div>
</form>
<form ng-show="showName3">
<div class="form-group">
<label>Field Label(?)</label>
<br/>
<input ng-model="field.single3">
</div>
</form>
</body>
</html>
here is plunkr http://plnkr.co/edit/oFytWlQMIaCaeakHNk71?p=preview
You will need "ng-repeat" in the HTML. Set an Array on $scope and let the template determine what HTML elements to add. Typically, $index is only set by ng-repeat.
Read more here: https://docs.angularjs.org/api/ng/directive/ngRepeat

Having trouble using ngChange to update model

I just started learning the basics of Angular. I'm attempting to making an annual salary converter, just for fun. I'm having difficulty with my monthly ng-model updating when the yearly model is changed by the user. The fields are input tags. Here is the code
<!doctype html>
<html ng-app="salaryApp">
<head>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/css/bootstrap.min.css" rel="stylesheet">
</head>
<body>
<div class="container" ng-controller="converter">
<h1>Salary converter</h1>
<div class="form-group">
<label>Annual Salary</label>
<input type="number" class="form-control" placeholder="0" ng-model="yearly" ng-change="reCalculate()" >
<br>
<label>Monthly Salary</label>
<input type="number" class="form-control" placeholder="0" ng-model="monthly" disabled>
</div>
</div>
<!--<div ng-controller="converter">
Write some text in textbox:
<input type="text">
<h1>Hello {{ yearly }}</h1>
<h1>Hello {{ monthly }}</h1>
</div>-->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/js/bootstrap.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script>
<!--<script src="salaryConverter.js"></script>-->
<script type="text/javascript">
var app = angular.module('salaryApp', []);
app.controller('converter', function($scope) {
$scope.yearly = 80000;
console.log("log1");
$scope.monthly = $scope.yearly / 12;
console.log("log2");
function reCalculate() {
console.log("function was run");
return $scope.yearly /12.00;
}
});
</script>
</body>
</html>
Here is the plnkr
http://plnkr.co/edit/26y0JRR7iVcrLOBlm7D2?p=preview
Youe need to use it as scope property. Here :
function reCalculate() {
console.log("function was run");
return $scope.yearly /12.00;
}
should be
$scope.reCalculate = function () {
console.log("function was run");
$scope.monthly=$scope.yearly /12.00;//Don't return, you neet to assign
}
Define function as in $scopeto be called from view and assign value to monthly instead of returning.
$scope.reCalculate = function () {
console.log("function was run");
$scope.monthly = $scope.yearly / 12.00;
}
DEMO
You need to add the reCalculate method to your scope:
app.controller('converter', function($scope) {
$scope.yearly = 80000;
$scope.reCalculate = reCalculate; <--- THIS LINE
console.log("log1");
$scope.monthly = $scope.yearly / 12;
console.log("log2");
function reCalculate() {
console.log("function was run");
return $scope.yearly /12.00;
}
});
You could also add it directly:
$scope.reCalculate = function()...
But I recommend to follow some style guides on how to write your controllers:
https://github.com/johnpapa/angular-styleguide
app.controller('converter', function($scope) {
$scope.yearly = 80000;
console.log("log1");
$scope.monthly = $scope.yearly / 12;
console.log("log2");
$scope.reCalculate = function () {
console.log("function was run");
$scope.monthly = $scope.yearly / 12;
}
});
Here is your plunker working

Truthy and falsey value (jQuery object)

I am implementing a function to check/uncheck radio buttons.
<!DOCTYPE html>
<html>
<head>
<title></title>
<script src = "http://code.jquery.com/jquery-2.1.4.min.js"> </script>
</head>
<body>
<form action="">
<input type="radio" name="sex" value="male" checked>Male<br>
<input type="radio" name="sex" value="female">Female
</form>
<script src = "../javascript/defaultCheckRadio.js"></script>
</body>
</html>
This code is doing the job, but I do not understand why the alert in the if block is never triggered. In my understanding, it should be triggered because all jQuery objects are truthy.
(function () {
var inElement = $('input');
var changeCheck = {
init: function () {
this.check();
},
check: function () {
$.each(inElement, function() {
var self = $(this);
if (self.checked) {
alert("if condition");
self.prop('checked',false);
} else {
alert("else");
self.prop('checked',true);
}
});
},
};
window.changeCheck = changeCheck.init();
})();
You have your if wrong, you are checking a javascript property on a jquery object, You should change:
if (self.checked) {
to:
if (self.prop('checked')) {
Just forget about jQuery and use vanilla-js:
if (this.checked) {
alert("if condition");
this.checked = false;
} else {
alert("else");
this.checked = true;
}
Note it can be simplified:
alert((this.checked = !this.checked) ? "else" : "if condition");

Categories

Resources