I have this line in my view:
<input placeholder="Search" type="text" ng-change="searchChange()" ng-model="mySearch" ng-model-options="{debounce: 1000}">
And then inside my controller I have:
angular.module('app.controllers', [])
.controller('listViewCtrl', ['$scope', '$stateParams', '$http',
function ($scope, $stateParams, $http) {
$http.get('http://www.domain.co.uk/api/search.php').
then(function(response) {
$scope.food = response.data;
});
$scope.searchChange = function() {
console.log($scope.mySearch);
};
}])
But this is giving me "undefined".
How can I reference the value of the mySearch input field in my controller?
Your input field might be located within a sperate scope, which is not updated correctly. ngIf and ng-repeat are common examples for directives creating a separate sub-scope. (See this article for more information around scopes)
Dotted scope variables
To protect yourself from such issues you might either store your variables inside objects.
<input placeholder="Search" type="text" ng-change="searchChange()" ng-model="my.search" ng-model-options="{debounce: 1000}">
$scope.my = {search: ""};
$scope.searchChange = function() {
console.log($scope.my.search);
};
Named Controllers
Or name your controllers specifically as recommended in the angular style guide Y030.
Pass variable as parameter
A third option is simply passing the variable as parameter to the function:
<input placeholder="Search" type="text" ng-change="searchChange(mySearch)" ng-model="mySearch" ng-model-options="{debounce: 1000}">
$scope.searchChange = function(mySearch) {
console.log(mySearch);
};
Related
I am really new to AngularJS. I want to pass some object from View (HTML) to my controller (JS).
Actually my Client will send me data in HTML and I have to take that data and process that data in my controller and then display the processed output on screen. He will be using some back-end technology called ServiceNow - https://www.servicenow.com/ .
All the solutions I saw had some event like click event or change event, but in my case this has to be done on page load.
I m using Input type hidden for passing the data to the controller, seems like it's not working.
So is there any other way I can do this ?
Here's the code I am trying to use
<div ng-controller="progressController" >
<input type="hidden" value="ABCD" ng-model="testingmodel.testing">
</div>
app.controller('progressController', function($scope) {
console.log($scope.testingmodel.testing);
});
It says undefined when I console.log my variable in Controller.
You're doing console.log(...) too early. At this time your controller doesn't have any information from the view.
The second problem is that you're binding the view to a variable in controller and not the other way around. Your $scope.testingmodel.testing is undefined and it will obviously the value in the view to undefined.
Solution
Use ng-init to initialize the model and the controller's hook $postLink to get the value after everything has been initialized.
Like this
<div ng-controller="progressController" >
<input type="hidden" ng-model="testingmodel.testing" ng-init="testingmodel.testing = 'ABCD'">
</div>
app.controller('progressController', function($scope) {
var $ctrl = this;
$ctrl.$postLink = function() {
console.log($scope.testingmodel.testing);
};
});
Edit: extra tip
I don't recomment using $scope for storing data since it makes the migration to newer angular more difficult.
Use controller instead.
Something like this:
<div ng-controller="progressController as $ctrl" >
<input type="hidden" ng-model="$ctrl.testingmodel.testing" ng-init="$ctrl.testingmodel.testing = 'ABCD'">
</div>
app.controller('progressController', function() {
var $ctrl = this;
$ctrl.$postLink = function() {
console.log($ctrl.testingmodel.testing);
};
});
You should use the ng-change or $watch
<div ng-controller="progressController" >
<input type="hidden" value="ABCD" ng-model="testingmodel.testing" ng-change="change()">
</div>
app.controller('progressController', function($scope) {
$scope.change = function(){
console.log($scope.testingmodel.testing);
}
});
Or:
app.controller('progressController', function($scope) {
$scope.$watch('testingmodel.testing', function(newValue, olValue){
console.log(newValue);
}
});
If you use ng-change, the function is only called if the user changes the value in UI.
If you use $watch anyway, the function is called.
You can't use value attribute for set or get value of any control, angularJS use ngModel for set or get values.
Here You should try like this way
app.controller('progressController', function($scope) {
//from here you can set value of your input
$scope.setValue = function(){
$scope.testingmodel = {}
$scope.testingmodel.testing = 'ABCD';
}
//From here you can get you value
$scope.getValue = function(){
console.log($scope.testingmodel.testing);
}
});
if you want to bind from html side then you should try like below
<input type="text" ng-model="testingmodel.testing">
<input type="hidden" ng-model="testingmodel.testing">
Below is my playlist json data coming from playlist controller.
{
"id":18,
"file":{"url":"/uploads/playlist/file/18/01_-_MashAllah.mp3"},
"event_id":23,"created_at":"2015-11-11T10:33:52.000Z",
"updated_at":"2015-11-11T10:33:52.000Z",
"name":"01 - MashAllah.mp3"
},
{
"id":19,
"file":{"url":"/uploads/playlist/file/19/02_-_Laapata.mp3"},
"event_id":19,"created_at":"2015-11-11T10:50:01.000Z",
"updated_at":"2015-11-11T10:50:01.000Z",
"name":"02 - Laapata.mp3"
}
Now i want to bind id and name to a playerController am i doing something like this
<div ng-controller="playlistsController">
<div ng-repeat="playlist in playlists">
<div ng-controller='PlayerController'>
<input type=hidden ng-model="ID" ng-init="ID=playlist.id">
<input type=hidden ng-model="Name" ng-init="Name=playlist.name">
</div>
</div>
</div>
and in controller
.controller('PlayerController',['$scope',function($scope) {
console.log($scope.ID);
console.log($scope.name);
}]);
but the console is showing undefined.
i don't know where i am going wrong as i am new to angular.
METHOD 1:
The best way to share data between controllers is to use services. Declare a service with getters and setters and inject into both the controllers as follows:
service:
app.service('shareData', function() {
return {
setData : setData,
getData : getData,
shared_data : {}
}
function setData(data) {
this.shared_data = data
}
function getData() {
return this.shared_data
}
})
With your service defined, now inject into both the controllers and use the parent controller (in your case) to set the data as follows:
app.controller('playlistsController', function(shareData) {
//your data retrieval code here
shareData.setData(data);
})
And finally in your child controller, get the data:
app.controller('PlayerController', function(shareData) {
$scope.data = shareData.getData();
})
METHOD 2:
Since, you have to communicate data from parent controller to child controller, you can use $broadcast as follows:
parent controller:
//retrieve data
$scope.$broadcast('setData', data);
And receive the data in child controller:
$scope.$on('setData', function(event, args) {
$scope.data = args;
})
First controller code is executed, then angular starts proceed html this controller is attached to. So just move your variable initialization to controller:
$scope.Name = $scope.playlist.name;
$scope.ID = $scope.playlist.id;
or just use original variables (if you dont need copy of them)
<input type=hidden ng-model="ID=playlist.id">
<input type=hidden ng-model="Name=playlist.name">
or you may leave it as is - it works disregarding that you don't see values in log.
You should use $parent:
JSFiddle
HTML:
<div ng-controller="playlistsController">
<div ng-repeat="playlist in playlists">
<div ng-controller='PlayerController'>
<input type="text" ng-model="$parent.playlist.id">
<input type="text" ng-model="$parent.playlist.name">
</div>
</div>
</div>
JS:
app.controller('PlayerController', function ($scope, $sce) {
console.log($scope.$parent.playlists);
});
Hey guys here is my code it is not running at all i can't understand i just want to understand why it is not running
http://plnkr.co/edit/vvv3aavAopBhXlc1miUI
var app = angular.module('plunker', []);
app.controller('MainCtrl', function($scope) {
$scope.user=$scope.name;
console.log($scope);
});
This line is wrong:
$scope.user=$scope.name;
You are trying to assign the value of one property on your scope (user) from a non defined property (name)
I think you should be using this kind of approach
app.controller('MainCtrl', function($scope) {
$scope.user="user"
$scope.name="name";
console.log($scope);
});
For demo purposes this will hard code 'user' and 'name' in your input fields, but if you are trying to capture values entered by the user you will probably be using a button with a click handler and in the handler function you can access the user and name values on your scope for further processing, e.g. submit to server via $http
From what I understand you want the second update field to get updated when you type something in the first.
Why it is not working now?
At the moment you are only assigning the value of $scope.name to $scope.user when the controllers loads at start (undefined). You are not watching the value and assigning it to $scope.user when it changes so the value of $scope.user does not update.
Some options on how to make it work
You could use the ngChange directive
In your HTML:
<input type="text" ng-model="name" ng-change="updateUser()">
<input type="text" ng-model="user">
in your controller:
$scope.updateUser = function() {
$scope.user=$scope.name; }
ng-change (Plunkr)
Or (depending on what you are trying to achieve), you could give them the same ng-model:
<input type="text" ng-model="name">
<input type="text" ng-model="name">
same ng-model (Plunkr)
If I have an angular form like this
<form name="myForm">
<input type="text" required ng-model="field1" />
<input type="text" ng-model="field2" />
</form>
When I access the model it will only hold those fields that have values so if both fields have values json will be {"field1":"value1","field2":"value2"}. If only field1 is has a value json will be {"field1":"value1"}. Can I instruct Angular to keep empty fields in the model with null values?
UPDATE:
My controller looks like below. I'm loading the data as json from the server. When the data comes from the server I get this {"field1":"value1","field2":"value2"} but when saveContent is run and only field1 has a value the server gets this {"field1":"value1"}.
var myApp = angular.module('myApp', []);
myApp.controller('contentEditController', ['$scope', '$http',
function ($scope, $http) {
$scope.saveContent = function () {
$http.post("/api/ContentData", $scope.formdata);
};
$scope.loadContent = function (contentId) {
$http.get("/api/ContentData/" + contentId)
.success(function (response) {
$scope.formdata = response;
});
}
}]);
So fields that had values when they came from the server don't get sent back as empty.
-Mathias
Initialize the values on the scope in the controller,
.controller('formcontroller', [ '$scope', function($scope){
$scope.field1 = "";
$scope.field2 = "";
})];
The proper way to do this is to initialize the variables. You should in your controller have
$scope.field1 = ""
$scope.field2 = ""
or a more crude way to do is in to use ng-init (try not to use ng-init if you can)
<input type="text" required ng-model="field1" ng-init="field1=''"/>
<input type="text" ng-model="field2" ng-init="field2=''"/>
http://jsfiddle.net/ntszE/
<input type="text" placeholder="0" ng-model="deposit" value="4" />€
alert('begin test');
alert($scope.deposit);
alert('end test');
What am I doing wrong in binding the input value to a scope variable?
You have to access the $scope in the controller. Check out the modification of your fiddle http://jsfiddle.net/lpiepiora/ntszE/2/
Basically you have to define a controller
function MyCtrl($scope) {
$scope.deposit = 4;
$scope.showValue = function() {
alert($scope.deposit);
};
};
and then bind it using the ng-controller directive: ng-controller="MyCtrl".
Assuming you have a controller defined -
The $scope isn't exposed to any javascript out there. If you want to access it you need to get it. You can do something like this:
var scope = angular.element('input').scope();
alert(scope.deposit);