Setting data-ng-model in JavaScript - javascript

I need to set the data-ng-model attribute of an html input field via javascript.
I know I can't do
element.data-ng-model = "...";
because of the dashes. So I tried
element.["data-ng-model"] = "...";
and
element.dataNgModel = "...";
and
element.datangmodel = "...";
None of these seem to work properly.
Any suggestions?

Try:
element.setAttribute("ng-model", "...");
or if you have JQuery:
$(element).attr("ng-model", "...");

If you need to set the model with javascript you can set it in the controller see below From the angular docs
https://docs.angularjs.org/api/ng/directive/ngModel
(function(angular) {
'use strict';
angular.module('getterSetterExample', [])
.controller('ExampleController', ['$scope',
function($scope) {
var _name = 'Brian';
$scope.user = {
name: function(newName) {
// Note that newName can be undefined for two reasons:
// 1. Because it is called as a getter and thus called with no arguments
// 2. Because the property should actually be set to undefined. This happens e.g. if the
// input is invalid
return arguments.length ? (_name = newName) : _name;
}
};
}
]);
})(window.angular);
<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.5.5/angular.min.js"></script>
<div ng-app="getterSetterExample">
<div ng-controller="ExampleController">
<form name="userForm">
<label>Name:
<input type="text" name="userName" ng-model="user.name" ng-model-options="{ getterSetter: true }" />
</label>
</form>
<pre>user.name = <span ng-bind="user.name()"></span></pre>
</div>
</div>

Related

How to detect changes in form and set new state?

I have HTML form with set of elements(inputs).
So, how to detect changes in any input and set new statement in object var data?
For example:
<input type="text" name="parameter" value="30">
When I make chnages in input I need to get output object data as:
var = data = ["paraeter" : 30];
for watch the value on change in angular you should use ng-change and ng-model
var app = angular.module("app", []).
controller("ctrl", function($scope) {
$scope.info = {
parameter: 30,
parameters: {
children: 40
}
};
$scope.callBackIfChange = function(){
console.log($scope.info);
}
})
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="ctrl">
<form>
<label>empty value</label>
<input type="text" ng-model="info.name" ng-change="callBackIfChange()">
<br>
<br>
<label>has default value</label>
<input type="number" ng-model="info.parameter" ng-change="callBackIfChange()">
<br>
<br>
<label>nested</label>
<input type="number" ng-model="info.parameters.children" ng-change="callBackIfChange()">
</form>
<hr>
<b>output:</b> {{info | json}}
</div>
Here is the Jquery code covering your cases (onload and input change) without hard-coding the name attributes of inputs tags:
var inputValuesObj = {}; // << Your Object
$(document).ready(function() {
getDefaultInputValues();
});
$(document).on("load keyup", "input", function() {
getDefaultInputValues();
});
function getDefaultInputValues() {
$("input").each(function(index) {
inputValuesObj[$(this).attr("name")] = $(this).val();
});
$("div#res").html(JSON.stringify(inputValuesObj));
}
Your test here - https://jsfiddle.net/uo08fedh/20/
Hope it helps!

How to bind a value from one ng-model to an other by matching a specific string

I got a requirement to bind a value to a particular model when the value in the other model contains a string starting with "https".
For example, I have two text fields both fields having different model
<input type="text" ng-model="modelText1">
<input type="text" ng-model="modelText2">
Suppose I type a value on the first text field "https", the first input model modelText1 have to bind to the second input model modelText2 and later on i have to maintain it as like two-way binding. i.e. the second field will automatically get the value dynamically when it contains "https" at starting of a string.
Try it like in this Demo fiddle.
View
<div ng-controller="MyCtrl">
<input type="text" ng-model="modelText1">
<input type="text" ng-model="modelText2">
</div>
AngularJS Application
var myApp = angular.module('myApp',[]);
myApp.controller('MyCtrl', function ($scope) {
$scope.modelText1 = '';
$scope.modelText2 = '';
var regEx = new RegExp(/^https/);
$scope.$watch('modelText1', function (newValue) {
if (newValue.toLowerCase().match(regEx)) {
$scope.modelText2 = newValue;
} else {
$scope.modelText2 = '';
}
});
});
An other approach is (that avoid using of $watch) is to use AngularJS ng-change like in this
example fiddle.
View
<div ng-controller="MyCtrl">
<input type="text" ng-model="modelText1" ng-change="change()">
<input type="text" ng-model="modelText2">
</div>
AngularJS Application
var myApp = angular.module('myApp',[]);
myApp.controller('MyCtrl', function ($scope) {
$scope.modelText1 = '';
$scope.modelText2 = '';
var regEx = new RegExp(/^https/);
$scope.change = function () {
if ($scope.modelText1.toLowerCase().match(regEx)) {
$scope.modelText2 = $scope.modelText1;
} else {
$scope.modelText2 = '';
}
};
});
You can use the ng-change directive like this:
<input type="text" ng-model="modelText1" ng-change="onChange()">
<input type="text" ng-model="modelText2">
and your controller:
$scope.onChange = function() {
if ($scope.modelText1 === 'https') {
$scope.modelText2 = $scope.modelText1;
else
$scope.modelText2 = '';
};
use ng-change to check the text is equal to 'https'
angular.module('app',[])
.controller('ctrl',function($scope){
$scope.changeItem = function(item){
$scope.modelText2 = "";
if(item.toLowerCase() === "https"){
$scope.modelText2 = item
}
}
})
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="ctrl">
<input type="text" ng-model="modelText1" ng-change="changeItem(modelText1)">
<input type="text" ng-model="modelText2">
</div>
EDiTED
to make sure it does't fail under 'HTTPS' use toLoweCase function to make all lower case
HTML :
<input type="text" ng-model="modelText1" ng-change="updateModal(modelText1)">
JS :
var modelText1 = $scope.modelText1.toLowerCase();
$scope.updateModal = function(){
$scope.modelText2 = '';
if(modelText1.indexOf('https')!=-1){
$scope.modelText2 = modelText1;
}
}
you could also possibly do this as a directive if you want to have a more reusable solution over multiple views http://jsfiddle.net/j5ga8vhk/7/
It also keeps the controller more clean, i always try to use the controller only for controlling complex business logic and business data
View
<div ng-controller="MyCtrl">
<input type="text" ng-model="modelText1" >
<input type="text" ng-model="modelText2" model-listener="modelText1" model-listener-value="https" >
</div>
Angular JS
var myApp = angular.module('myApp',[]);
myApp.controller('MyCtrl', function ($scope) {
$scope.modelText1 = '';
$scope.modelText2 = '';
});
myApp.directive('modelListener', [function() {
return {
restrict: 'A',
controller: ['$scope', function($scope) {
}],
link: function($scope, iElement, iAttrs, ctrl) {
$scope.$watch(iAttrs.modelListener, function() {
if($scope[iAttrs.modelListener] === iAttrs.modelListenerValue ) {
$scope[iAttrs.ngModel] = $scope[iAttrs.modelListener];
} else {
$scope[iAttrs.ngModel] = "";
}
}, true);
}
};
}]);

accessing attribute directive values using controller as

I know how to do it Without controller as:
html
Let's assume I have a directive named ngUpperCase(either true or false)
<div ng-controller="myControl" >
<input type="text" ng-upper-case="isGiant" >
</div>
Js
myApp.directive('ngUpperCase',function(){
return{
restrict:'A',
priority:0,
link:function($scope,element,attr){
//---to retrieve value
var val = $scope[attr.ngUpperCase];
var anotherVal = $scope.$eval(attr.ngUpperCase);
$scope.$watch(attr.ngUpperCase,function(val){
//---to watch
})
}
};
})
How to make the directive if I'm using something like this?
<div ng-controller="myControl as ctl" >
<input type="text" ng-upper-case="ctl.isGiant" >
</div>
Since it's not very clear what you want to achieve, here is an example of doing what I understand you need: changing an input value to upper or lower case depending on a variable:
function ngUpperCase() {
return{
restrict:'A',
priority:0,
link:function($scope,element,attr){
//---to retrieve value
var val = $scope[attr.ngUpperCase];
var anotherVal = $scope.$eval(attr.ngUpperCase);
$scope.$watch(attr.ngUpperCase,function(val){
if(val) {
element[0].value = element[0].value.toUpperCase();
} else {
element[0].value = element[0].value.toLowerCase();
}
})
}
}
}
function myController() {
this.isGiant = true;
}
angular.module('myApp', []);
angular
.module('myApp')
.controller('myController', myController)
.directive('ngUpperCase', ngUpperCase);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.6/angular.min.js"></script>
<div ng-app="myApp">
<div ng-controller="myController as ctl" >
lower case<br>
upper case
<input type="text" ng-upper-case="ctl.isGiant" value="TeStiNg123" >
</div>
</div>

Angular ng-model values not registered on submit

I know the title is kind of ambiguous but here is the issue: I have 2 input fields in a form that look like this:
<form name="modifyApp" class="form-signin" ng-submit="modify(val)">
<input type="text" class="form-control" ng-model="val.name" id="appName">
<input type="number" class="form-control" ng-model="val.number" id="number" min="0" max="65535">
<button type="submit">Submit</button>
</form>
When I load the page I populate those two with some values from inside the controller:
angular.module('myApp').controller('modifyAppController', ['$scope', function($scope) {
function setFields(appName, appNumber){
document.getElementById("appName").value = appName
document.getElementById("number").value = appNumber
}
$scope.modify= function(val){
console.log(val)
}
}])
The problem is when I press the Submit button. The values won't get registered unless I change them. For example, if I press the Submit button nothing gets printed, but if I change the number or the name, it gets printed.
In your controller you can simply initialize the val object like this:
angular.module('myApp', [])
.controller('modifyAppController', ['$scope', function($scope) {
$scope.val = {
name: '',
number: 0
};
function setFields(appName, appNumber) {
$scope.val.name = appName;
$scope.val.number = appNumber;
}
$scope.modify = function(val) {
console.log(val);
};
}]);
You need to rewrite your controller:
angular.module('myApp').controller('modifyAppController', ['$scope', function($scope) {
$scope.val = {
name = 'My app name',
number = '1'
};
function setFields(appName, appNumber){
$scope.val.name = appName;
$scope.val.number = appNumber;
}
$scope.modify= function(){
console.log($scope.val);
}
}])
You don't need to directly modify the DOM values in Angular. All your $scope variables are available in your template.
why not just have the following as the first line in your form
<form name="modifyApp" class="form-signin" ng-submit="modify()">
and then your controller can look like this
$scope.val = {
name: '',
number:0//some default values
}
$scope.modify= function(){
console.log($scope.val)
}

Concatenate (append) one input field value to another field in angular form

Trying to auto-populate first input field value into second input field value, However if the second input field as existing values then i would like to append / concatenate the first input field value to second.
logic:
if ( second ){
second = first + second;
}else{
second = first;
}
html:
<input type='text' ng-model='owner' required class="form-control">
<input type='text' ng-model='member' required class="form-control">
code:
app.controller("Controller", ['$scope', function($scope){
$scope.$watch(function () {
return $scope.owner;
},
function (newValue, oldValue) {
if ( $scope.member ){
$scope.member = $scope.owner + ',' + $scope.member;
}else{
$scope.member = newValue;
}
}, true);
}]);
plunker
Update (problem):
When i type Jake in Owner Field, it loops through the letters and print's as Jake,Jak,Ja,Jin member field. If i have pre-existing value Adam in member field, upon entering Tom in owner filed it will create Tom,To,T,Adam in member field. Please check the plunker for demo.
Mad-D consider changing your approach as it is prone to a circular dependency based on the way ng-model works.
You already have access to both values and you can display it in other ways. Plus your controller looks cleaner and acts as a true view model (vm):
Plunker
app.controller("Controller", function(){
var myCtrl = this;
myCtrl.owner = "";
myCtrl.member = "";
});
I have created a plnkr
. And also given below. Check whether it's correct one for you.
var app = angular.module('form-example1', []);
app.controller("Controller", ['$scope', function($scope){
$scope.permaMember = $scope.member?$scope.member:'';
$scope.editSecond = function(member){
$scope.permaMember = member?member:'';
}
$scope.editFirst = function(owner){
if(owner){
$scope.member = $scope.permaMember + owner
}
else{
$scope.member = $scope.permaMember
}
}
}]);
<!doctype html>
<html ng-app="form-example1">
<head>
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/angularjs/1.2.0-rc.2/angular.min.js"></script>
<script type="text/javascript" src="script.js"></script>
</head>
<body>
<div ng-controller="Controller">
<form name="testform">
<div class='form-group'>
<label>Owner</label>
<input type='text' ng-model='owner' required class="form-control" ng-change="editFirst(owner)">
</div>
<div class='form-group'>
<label>Member</label>
<input type='text' ng-model='member' required class="form-control" ng-change="editSecond(member)">
</div>
<button ng-disabled="testform.$invalid" ng-click ="submit()">SAVE</button>
</form>
</div>
</body>
</html>
Why not just have a 3rd read only text box or label that displays $scope.owner, $scope.member?

Categories

Resources