Model is not reflected when I use same controller with two divs - angularjs

I have given same controller in two divs but model that gets updated in one div does not reflect in another.
<body ng-app="myApp">
<div ng-controller="filterCtrl">
<p ng-bind="test" />
</div>
<div ng-controller="filterCtrl">
<p><input type="text" ng-model="test" ng-change="handleChange()"></p>
</div>
</body>
When I am entering into the text box it's not updating the above div's "ng--bind". Though, if I put that "ng-bind" in the div having text box, it's working fine. Kindly help me on this.

it should be like that
<html ng-app="myApp">
<body ng-controller="filterCtrl">
<div>
<p>{{test.text}}</p>
</div>
<div>
<p><input type="text" ng-model="test.text" ng-change="handleChange()"></p>
</div>
</body>
</html>
here example on plunker

Nothing bad to reuse controller in your code: fiddle
As you can see they both works, but independently.
It's because each other instantiate its own scope. If you want them to talk, you can to make it via some services or to create some common scope for both of them, or merge them into one controller instance.
You can use parent scope as common part for both.
<div ng-controller="MainCtrlr as c">
<input ng-model="$parent.name" />
Hello, {{$parent.name}}!!!
</div>
<div ng-controller="MainCtrlr as c">
<input ng-model="$parent.name" />
Hello, {{$parent.name}}!!!
</div>
Fiddle
Talk via services will be much better than this:
Code:
angular.module('app', [])
.controller('MainCtrlr', ['MainData', function(MD){
this.MD = MD;
MD.name = 'World';
}]).service('MainData', [function(){}])
Template:
<div ng-controller="MainCtrlr as c">
<input ng-model="c.MD.name" />
Hello, {{c.MD.name}}!!!
</div>
<div ng-controller="MainCtrlr as c">
<input ng-model="c.MD.name" />
Hello, {{c.MD.name}}!!!
</div>
Fiddle

Problem:
If we try to associate same controller with two divs then angular creates two different scopes for those two divs.
And if we try to update scope in one instance then it will not be reflected to other instance.
There are two ways to get rid of from this situation:
You can create one mainCntrl that have filterCtrl as its child controller.
And assumed mainCntrl has mainView scope property. We created a mainView object on the mainCntrl,
and since filterCtrl and its scope prototypally inherit from mainCntrl so we can always reach that mainView in any instance of filterCtrl.
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<html>
<head>
<script>
angular.module('myApp', [])
.controller('mainCntrl', function($scope) {
$scope.mainView = {};
$scope.mainView.x = 'Something';
})
.controller('filterCtrl', function($scope) {
});
</script>
</head>
<body ng-app="myApp">
<div ng-controller="mainCntrl">
<div ng-controller="filterCtrl">
<p ng-bind="mainView.x" />
</div>
<div ng-controller="filterCtrl">
<p><input type="text" ng-model="mainView.x" ng-change="handleChange()"></p>
</div>
</div>
</body>
</html>
We can utilized $parent which can be accessed through $scope.$parent. This place will be the common place for all the instances of filterCtrl.
So whatever we put over $scope.$parent, will be accissible to all the instances.
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<html>
<head>
<script>
angular.module('myApp', [])
.controller('filterCtrl', function($scope) {
$scope.$parent.test = 'Something';
});
</script>
</head>
<body ng-app="myApp">
<div ng-controller="filterCtrl">
<p ng-bind="$parent.test" />
</div>
<div ng-controller="filterCtrl">
<p><input type="text" ng-model="$parent.test" ng-change="handleChange()"></p>
</div>
</body>
</html>

Related

Angular: Clear User Input on ng-hide

Using Angular, I am trying to find away to clear the user input inside a div when its visibility is toggled using ng-show. Ideally, when the conditions are met that cause the div to disappear, it should remove all of the user selected data from the div. Any help would be appreciated!
<html>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<body ng-app="">
<div>
<input type="checkbox" ng-model="varA" ng-init="varA=false"> Item 1
</div>
<div ng-model="varB" ng-show="varA==false">
<input type="checkbox"> Item 2
</div>
</body>
</html>
Use ngChange on your checkbox:
<input type="checkbox" ng-change="checkboxChanged()" ng-model="varA" ng-init="varA=false">
Then in your controller implement the checkboxChanged function:
$scope.checkboxChanged = function() {
$scope.varB = '';
};
By the way, ngModel is meant only for input, select, and textarea only. Do not use ngModel with a div.
You can use the ng-reset-on directive I've written. It can resets all fields based on an expression. You need to specify a controller and the field must have a ng-model.
(function(){
angular.module("app", ["ng-reset-on"]);
angular.module("app").controller("AppCtrl", function() {});
})();
<html>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<script src="https://cdn.rawgit.com/waldirpereira/angular-reset-on/master/dist/angular-reset-on.js"></script>
<body ng-app="app">
<div ng-controller="AppCtrl">
<div>
<input type="checkbox" ng-model="varA" ng-init="varA=false"> Item 1
</div>
<div ng-show="varA==false">
<input type="checkbox" ng-model="varB" ng-reset-on="varA==true"> Item 2
</div>
</div>
</body>
</html>

why ng-model initial value not get displayed

I am new to Angular JS. Here is my html :
<!DOCTYPE html>
<html>
<head>
<title>My App</title>
<script src = "angular.js"></script>
</head>
<body ng-app="myApp">
<div ng-controller="index">
{{message}}
</div>
<form>
First Name:<br>
<input type="text" ng-model="user.username">{{user.username}}<br>
Last Name:<br>
<input type="password" ng-model="user.password">
</form>
<script src = "app.js"></script>
<script src = "credentials.js"></script>
</body>
</html>
Then I want to initialize some data for username and password :
(function(){
var app=angular.module("myApp",[]);
app.controller("index", ["$scope", function($scope){
$scope.message="Hello, it's me!";
$scope.user={
username: "admin",
password: "admin"
};
}]);
})();
The username and password doesn't get displayed. Why?
You're problem is that you have bound the controller to the div-tag surrounding the {{message}} expression and not the whole block containing the form. If bind your controller to a surrounding element youre code will work as expected.
Here's one way to do this:
<body ng-app="myApp">
<div ng-controller="index">
<div>
{{message}}
</div>
<form>
First Name:<br>
<input type="text" ng-model="user.username">{{user.username}}<br>
Last Name:<br>
<input type="password" ng-model="user.password">
</form>
</div>
</body>
Your controller div is not covering the area where you have user object. controller div must include the code in which you are accessing user object
You can change the code like this
<body ng-app="myApp">
<div ng-controller="index">
{{message}}
<form>
First Name:<br>
<input type="text" ng-model="user.username">{{user.username}}<br>
Last Name:<br>
<input type="password" ng-model="user.password">
</form>
</div>
<script src = "app.js"></script>
<script src = "credentials.js"></script>
</body>
<div ng-app="">
<p>Name: <input type="text" ng-model="name"></p>
<p ng-bind="name"></p>
</div>
as you can see in this example
ng-model directive binds the value of HTML controls (input, select,
textarea) to application data. ng-bind directive binds application
data to the HTML view.
i can see ng-model in your code but there is not ng-bind which actually binds data to your view. probably that is the reason why your code is not displaying username and password.
With the ng-model directive you can bind the value of an input field to a variable created in AngularJS.
You can use the ng-bind directive, which will bind the innerHTML of the element to the specified model property:
ng-model for input elements like input, textarea and ng-bind for h1,label etc.
<!DOCTYPE html>
<html>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<body>
<div ng-controller="index" ng-app="myApp">
<form>
First Name:
<br>
<input type="text" ng-model="user.username">
<br> Last Name:
<br>
<input type="password" ng-model="user.password">
</form>
</div>
<script>
var app = angular.module("myApp", []);
app.controller("index", ["$scope", function($scope) {
$scope.user = {
username: "admin",
password: "admin"
};
}]);
</script>
</body>
</html>
As,Venu prasad H S and domyos already suggested , a reply to the comment of M. Ko as i don't have enough reputation to comment,
You have defined the ng-model out of the scope of the controller,
<div ng-controller="index">
{{message}}
</div>
What this does is that your controller can access only the stuff inside this div only, as many others suggested you can put an entire div in the body you can do
<body ng-app="myApp">
<div ng-controller="index">
<div>
{{message}}
</div>
<form>
First Name:<br>
<input type="text" ng-model="user.username">{{user.username}}<br>
Last Name:<br>
<input type="password" ng-model="user.password">
</form>
</div>
As very aptly provided by domyos , now what this does is that your controller can get to your form and you can display the values you desire.
Alternatively you can also but your controller in the body tag with your ng-app
<body ng-app="myApp" ng-controller="index">
but it is recommended that you put it inside a div, you want to do this so that you can have multiple controllers in one module i.e. on ng-app.
Also, try to name controller as "indexCtrl" as in IndexController it is just a naming convention but that makes your code more readable.
Hope you find this information useful.
Use ng-app and ng-controller directives in your HTML page.
Here is link of Plunker for the same.
Plunker
And donot forget to give reference
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>

Open a div after clicking on first checkbox using Angular Js 1.5.0

I am new, trying my hands on angular. I made a list of checkbox using ng-repeat, there are five checkboxes and want to open a div only clicking on first checkbox. Don't know how to open.
Plunker
Thank you all in advance...
You can bind the model with checkbox and can toggle the display of the div based on the model value of the desired checkbox. I have created one plnkr for same: http://plnkr.co/edit/zcHbuwsUehDfBkgJWlIc?p=preview
HTML code
//HTML
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Example - example-example12-production</title>
<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js"></script>
<script src="script.js"></script>
</head>
<body ng-app="docsSimpleDirective">
<div ng-controller="Controller">
<div ng-repeat="cb in chkboxArr">
<input type="checkbox" ng-model="chkboxArrModel[$index]">{{$index}}
</div>
<div ng-if="chkboxArrModel[0]">Toggle me with first checkbox</div>
</div>
</body>
</html>
and Javascript code
//JS
(function(angular) {
'use strict';
angular.module('docsSimpleDirective', [])
.controller('Controller', ['$scope', function($scope) {
$scope.chkboxArr = [1,2,3,4];
$scope.chkboxArrModel = [];
}]);
})(window.angular);
Here is an example:
<div ng-show="checkbox1">Show me</div>
<input type="checkbox" ng-model="checkbox1"/>
<input type="checkbox" ng-model="checkbox2" />
<input type="checkbox" ng-model="checkbox3" />
Try this
<div ng-show="chk1">Div1</div>
<input type="checkbox" ng-model="chk1"/>
You can create a div like this:
<div ng-show="ModelData.Passengers == 'One'">
The actual div content you have in the div you want.
</div>
Assuming your radio buttons code to be like this:
<div>
<label>
<input type="radio" id="PassengersId1" name="PassengersName1" ng-model="ModelData.Passengers" value="One" />One
<input type="radio" id="PassengersId2" name="PassengersName2" ng-model="ModelData.Passengers" value="Two" />Two
</label>
</div>

ng-controller App data not binding properly

I have to finish this assignment. I am trying to print out the contacts in contactsController and be able to add to this list. I can't figure out where I am going wrong. Can anyone help. I have an array contacts[] in contactController and I am trying to print out the list in html using ng-repeat="contact in contactsController.contacts" and binding to contact.name and contact.type.
<!doctype html>
<html ng-app>
<head>
<style>
</style>
<link rel="stylesheet" type="text/css" href="style.css">
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.16/angular.min.js"></script>
</head>
<body>
<div ng-controller="contactsController">
<label>Name</label>
<input ng-model="contactsController.contacts.name" type="text" placeholder="Name">
<label>email</label>
<input ng-model="contactsController.email" type="text" placeholder="Email">
<button ng-click="addContact()">Add contact</button>
</div>
<div>{{contactsController.name}}</div>
<div>
<ul>
<li ng-repeat="contact in contactsController.contacts">
<div>{{contact.name}}</div>
<div>{{contact.email}}</div>
<div><button ng-click="deleteContact($index)">delete</button></div>
</li>
</ul>
</div>
<script>
// Your code goes here.
// $( document ).ready(function() {
// alert('jQuery asdfas!');
// Your code here.
// });
function contactsController($scope){
$scope.contacts=[{name:'asdf',email:'asdf'},
{name:'yweuir',email:'xcvzx'}
];
contactsController.prototype.addContact =function($scope){
console.log(this.name);
console.log(this.email);
this.contacts.push({name:this.name,email:this.email});
}
}
</script>
</body>
</html>
Your repeat is wrong. It should be:
ng-repeat="contact in contacts"
When you are doing a repeat, the reference to the array assumes it's in $scope already. Your controller has nothing to do with it. So if you had:
$scope.contractsController = {
contacts: {...}
}
Your code would work. But your controller is fine, just remove the reference from the repeat.
I'll create a plunker so you can check the detail changes in the revisions.
http://plnkr.co/edit/NrbLiIFw4EbxEfYJm41J?p=preview
The HTML had a wrong indentation, and the ng-repeat was outside of the ng-controller block.
Also, was missing the injection of the controller into the module of the application, i rewrote the application using the general application declaration with ngApp directive.
If you want an example more detailed you can check the TodoMVC angular application
https://github.com/tastejs/todomvc/tree/gh-pages/architecture-examples/angularjs-perf
Other examples:
http://todomvc.com/architecture-examples/angularjs/#/
All the best
Hey I'll create a plnkr link.
Here is link Check this:
http://plnkr.co/edit/mzcAC5yU9P6Mb3nfGByP?p=preview
Here is Code:
<!DOCTYPE html>
<html ng-app = "app">
<head>
<link rel="stylesheet" type="text/css" href="style.css">
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.16/angular.min.js">
</script>
<script>
angular.module("app",[]).controller('contactsController',['$scope',
function($scope) {
$scope.contacts=[{name:'Abhi',email:'Abhi#test.com'},
{name:'Sharma',email:'sharma#test.com'}
];
$scope.addContact =function(){
this.contacts.push({name:this.name,email:this.email});
$scope.name = '';
$scope.email = '';
}
$scope.deleteContact = function (index) {
$scope.contacts.splice(index, 1);
}
}
]);
</script>
</head>
<body ng-controller="contactsController">
<label>Name</label>
<input ng-model="name" type="text" placeholder="Name">
<label>email</label>
<input ng-model="email" type="text" placeholder="Email">
<button ng-click="addContact()">Add contact</button>
<div>
<ul>
<li ng-repeat="contact in contacts">
<div>{{contact.name}}</div>
<div>{{contact.email}}</div>
<div><button ng-click="deleteContact($index)">delete</button></div>
</li>
</ul>
</div>
</body>
</html>
May be it help you..
Thanks
You don't prefix your values with the controller name. The ng-controller section basically sets the scope for the child elements to an instance of the controller. So what's happening in your code currently is that it's checking the contactsController for an attribute of contactsController.

Using multiple controllers defined via module does not work

When defining controllers as global functions, everything works fine. But when using the modules to declare and "assign" the controllers, only the first controller is used to resolve the bindings. What am i missing?
<!doctype html>
<html>
<head/>
<body>
<div ng-app="flintstones">
<div ng-controller="flintstoneCtrl">
<label>Name:</label>
<input type="text" ng-model="yourName" placeholder="Enter a name here">
<hr>
<h1>Hello {{yourName}}!</h1>
</div>
</div>
<div ng-app="rumbles">
<div ng-controller="rumbleCtrl">
<label>Name:</label>
<input type="text" ng-model="yourName" placeholder="Enter a name here">
<hr>
<h1>Hello {{yourName}}!</h1>
</div>
</div>
</body>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.6/angular.min.js"></script>
<script>
var flintstones = angular.module("flintstones", []);
flintstones.controller("flintstoneCtrl", function flintstoneCtrl($scope) {
$scope.yourName = "Fred";
});
var rumbles = angular.module("rumbles", []);
rumbles.controller("rumbleCtrl", function rumbleCtrl($scope) {
$scope.yourName = "Barney";
});
</script>
</html>
#Arun is correct. However, in your case I'm guessing you don't really want to bootstrap Angular twice, but simply use controllers defined in different modules.
This is usually done by having a page/site module which have dependencies on all modules required, in your case flintstones and rumbles.
angular.module('flintstones', []).controller('flintstoneCtrl', ...);
angular.module('rumbles', []).controller('rumbleCtrl', ...);
// Create a module with dependencies.
angular.module('myApp', ['flintstones', 'rumbles'])...
In your html, you then simply use ng-app="myApp" and content from that module and all its dependencies will be accessible.
<html ng-app="myApp">
<body>
<div ng-controller="flintstoneCtrl">...</div>
<div ng-controller="rumbleCtrl">...</div>
</body>
</html>
I think, one page can have only one ng-app as default, in your case you have two ng-app definitions.
If you have multiple apps in a page you have to do manual bootstrapping

Resources