How get access to variable in Angular JS? - angularjs

I have next Angular JS controllers structure:
<div ng-controller="MainController">
<div ng-controller="mainCtrlTst">
// here is loaded HTML file
</div>
</div>
HTML file:
<div ng-controller="MainController">
<input ng-model="formData.map" value="">
</div>
For default formData.map containts address "USA, New York"
I have method Save() in MainController, but when I call this method I get:
console.log(formData.map); // undefined
How I can get value formData.map from input?

You should declare your model in controller like
$scope.formData = {
map: ''
};
And then use it in the view.
And then check in the save method by following code
console.log($scope.formData.map);
Hope you will not get undefined.

Try the following in MainController:
console.log($scope.formData.map);
To be more precise, in your save() function inside the controller do as follows:
$scope.save = function(){
console.log($scope.formData.map);
}
To know more about $scope, visit : https://docs.angularjs.org/guide/scope

Related

What is the advantage of controller without scope?

Just see the code
var angApp = angular.module('angApp',[]);
angApp.controller('testController', ['$http', function ($http) {
var self = this;
self.name ='Hello';
self.btnClick=function(){
self.name ='Hello! Button Clicked';
}
}]);
<html>
<head>
</head>
<body data-ng-app="angApp" data-ng-controller="testController as model">
<div>
{{model.name}}
</br>
<input type="button" value="Click" data-ng-click="model.btnClick();"/>
</div>
</html>
Now, tell me if we avoid scope and declare controller like this way testController as model then what will be an advantage or is it only syntactic sugar?
Basically, $scope has been removed as of Angular 2. In addition to that, the angular documentation specifically recommends using this instead of $scope.
Take a look at this article for more information: https://johnpapa.net/angularjss-controller-as-and-the-vm-variable/
And also check the accepted answer on this question: 'this' vs $scope in AngularJS controllers
Once advantage I can think about is, if you have nested controllers, for instance
<div ng-controller="myFirstController as ctrl1">
<div ng-controller="mySecondController as ctrl2">
{{ctrl1.someValue}}
</div>
</div>
It is easier and more clear when trying to reference a variable on the parent controller

how to use angular js scope variable in html

I want to pass value of scope variable returned from controller in html window.open, but the problem is i get some garbage value, please see the code below.
<header>
<span class="item-title">{{x.name}}</span>
<span class="list-item-note-sendmoney1" onclick="window.open('tel:{{x.phone}}', '_system')"><ons-icon icon="ion-android-call"></ons-icon></span>
</header>
<p class="swipe-item-desc">{{x.phone}}</p>
I want to pass {{x.phone}} to window.open('tel:') function.
Don't use onclick. Use ng-click. And put the JS code in the controller:
ng-click="openWindow()"
and in the controller
$scope.openWindow = function() {
window.open('tel:' + $scope.x.phone, '_system');
}

ngRepeat not updating after model changed

I'm tring to code a little search input to get data from a database using ngResource.
the data are shown in the page with a ng-repeat, but when i do the search and the $scope has been updated, the view is not updated and show old data.
Here is the code:
main.html (active view)
<div ng-controller="searchCtrl as searchCtrl" layout="column">
<form class="form-inline search-form col-md-offset-1">
<div class="form-group col-md-5">
<label class="sr-only" for="search_location">Location</label> <input
id="search_location" type="search" class="form-control"
ng-Autocomplete ng-model="place" placeholder="Location" />
</div>
<div class="form-group col-md-5">
<label class="sr-only" for="search_tags">Tags</label> <input
style="width: 100%;" id="search_tags" type="search"
class="form-control" id="search_tags" placeholder="Tags">
</div>
<div class="col-md-1">
<md-button class="md-fab md-mini" aria-label="Search" ng-click="searchCtrl.search()"> <md-icon class="md-fab-center"
md-font-icon="glyphicon glyphicon-search" style="color: black;"></md-icon>
</md-button>
</div>
</form>
</div>
<div ng-controller="mainCtrl">
<div ng-repeat="evento in eventi" ng-include="'views/components/event_card.html'" class="col-md-3"></div>
</div>
main.js
'use strict';
app.factory('Eventi', function($resource) {
return $resource('/eventsws/events/:location', {location : '#location'}, {
search: {
method: 'GET',
params: {
'location' : "#location"
},
isArray : true
}
})
});
app.controller('mainCtrl', function($scope, Eventi) {
$scope.eventi = Eventi.query();
});
searchbar.js
'use strict';
app.controller('searchCtrl', function($scope, Eventi) {
$scope.place = null;
this.search = function() {
$scope.eventi = Eventi.search({
'location' : $scope.place
});
}
});
when it start it get all the data from the database and display them correctly, when i try to make a search, the $scope.eventi is updated (i can see the new data in $scope.eventi from the debug) but the view still show the old data and never update.
I've tried to use $scope.$apply at the end of the search function but the result is the same.
Have you any idea why it's not working?
Thanks for your time.
The $scope.eventi you see in the debug is the one in your searchCtrl and not the one from your mainCtrl. To update your mainCtrl $scope.eventi you have to find an other way.
A clean but long solution would be using services to shares variables in your controllers.
To answer the question in comments :
i can see it updated, but the view still show the old data
I guess what's the problem (even if i actually didn't see your code).
Problem
If you bind your var like this :
Service
[...]
service.serviceVar = 1;
return service
[...]
This will create a "1" var with a reference.
Controller
[...]
$scope.myvar = Service.serviceVar;
[...]
This will bind $scope.myvar to the "1" reference.
If you do this in your service or in an other controller :
service.serviceVar = 2;
You will create a new var "2" with a new reference and you will assign this reference to service.serviceVar. Badly all your old references to the old 1 var will not update.
Solution
To avoid that do it like this :
Service
[...]
service.servicevar = {};
service.servicevar.value = 1;
return service
[...]
You create an object with a new reference and assign it to servicevar.
You create a var "1" and assign it to servicevar.value.
Controller
[...]
$scope.myvar = Service.servicevar;
[...]
You assign the servicevar reference to your scope var.
view
{{myvar.value}}
You can use the value by using the property of your var.
Updating the var doing this :
service.servicevar.value = 2;
You will create a new var "2" with a new reference and replace the old reference by this one.
BUT this time you keep all your references to servicevar in your controllers.
I hope i was clear and it answer your question.
EDIT :
Try to never ever use $scope.$apply. It's a really bad practice. If you use that to make something works, you should probably find an other to do that (And it will be a great question for Stacks i guess : "Why do i need $apply to solve my problem XXXXX")
rsnorman15 has a good point about your uses of asynchronous calls. Take a look at his answer too.
Here is one of my old plunker using a service to share properties
Just change:
$scope.eventi = Eventi.search({
'location' : $scope.place
});
to
Eventi.search({
'location' : $scope.place
}, function(eventi) {
$scope.eventi = eventi
});
It's an asynchronous call so it must be assigned in the success handler.
Another issue you are running into is your ng-repeat is not contained within the div that searchCtrl is scoped. Update your HTML so that it is contained like so:
<div ng-controller="searchCtrl as searchCtrl" layout="column">
<form class="form-inline search-form col-md-offset-1">
... form stuff
</form>
<div ng-repeat="evento in eventi" ng-include="'views/components/event_card.html'" class="col-md-3"></div>
</div>

Why this doesnt fire ng-repeat?

My HTML
ng-app and ng-controller are specified in markup earlier
<div class="statusEntry" ng-repeat="statusInput in statusInputs">
<span class="userName"> a </span>
<span class="statusMsg"> b </span>
</div>
Controller
app.controller('globalCtrl', ['$scope', function($scope) {
//someWork
pubnub.subscribe({
channel: "statuses",
callback:
function (data) {
splitData = data.split(';');
prepData = '{'+splitData[0]+','+splitData[1]+'}';
statusInputs.push(prepData);
}
});
When I push the data no new object appears.
Your Controller has no name.
You haven't declare an ng-app or ng-controller in your markup anywhere.
data should be named $scope so Angular can appropriately inject the dependency.
It doesn't look like either statusInputs or your function are part of the $scope therefore there's no way for your view to access them.
Replace
statusInputs.push(prepData);
with
$scope.statusInputs.push(prepData);
This is how you enable your views to access them.

How to use a JS variable which is passed to ejs template for angular app?

Given an EJS template which is rendered with expressJS, I have a variable itemId. How can I use it in the MyCtrl controller?
<script>x="<%=itemId%>"</script>
<div ng-controller="MyCtrl">
</div>
So far I have tried
<script>$scope.x=<%=itemId%></script>
and then in the controller, try to fetch it with $scope.x but it does not work.
You may need to add quotes around your var if it is a string or zero padded number.
<script>x="<%=itemId%>";</script>
<div ng-controller="MyCtrl">
</div>
Also, you need to set it to your $scope'd value (in your controller). Assuming you have your controller in another JS file somewhere else in your code
function MyCtrl($scope){
$scope.x = window.x;
}

Resources