Paramaters of $scope.function becomes undefined - angularjs

I have this html
<div ng-controller = "RetrieveCtrl as retrieve" >
<form>
<input ng-model = "retrieve.input1">
<input ng-model = "retrieve.input2">
<button type="submit" ng-click="retrieve.retrieveEntry()">Search</button>
.
.
.
with this controller
app.controller('RetrieveCtrl', ['$scope' , '$http', function($scope, $http) {
$scope.retrieveEntry = function () {
var input1 = $scope.retrieve.input1;
var input2 = $scope.retrieve.input2;
// validate input1 & input2 first...
// input1 & input2 part of URL
$http.get(...
)
};
}
which is working fine, I was able to retrieve my data from the web service. What I want to do is to refactor the function into two:
app.controller('RetrieveCtrl', ['$scope' , '$http', function($scope, $http) {
$scope.clickSearch = function() {
var input1 = $scope.retrieve.input1;
var input2 = $scope.retrieve.input2;
// validate input1 & input2 first...
$scope.retrieveEntry(input1, input2);
};
$scope.retrieveEntry = function (a, b) {
// build a and b in URL
$http.get(...
)
};
}
so that I could reuse $scope.retrieveEntry on other functionalities. However, a and b becomes undefined, after I split the function into two (button's ng-click is updated to "retrieve.clickSearch()"). I suspect it has to do with $scope, which I don't have much clear understanding of what's going on (I'm still quite confused with this and $scope) Could someone explain what's happening behind and how to resolve this?
Thanks.

I am not sure whether this would solve your issue, but you are not making correct use of controller as syntax. You controller implementation should look something like this:
app.controller('RetrieveCtrl', ['$scope' , '$http', function($scope, $http) {
var self=this;
self.clickSearch = function() {
// validate input1 & input2 first...
self.retrieveEntry(self.input1, self.input2);
};
self.retrieveEntry = function (a, b) {
// build a and b in URL
$http.get(...
)
};
}
Once you start using controller as syntax you mostly add functionality to your controller not scope directly.

Related

Data not passing between Controllers

Hi I am trying to pass data from one Controller to another but the data is not displaying on the other end of UI .
this is my service code :-
app.factory('ServiceF', function($rootScope) {
var service = {};
service.data = false;
service.sendData = function(data){
this.data = data;
$rootScope.$broadcast('data_shared');
};
service.getData = function(){
return this.data;
};
return service;
});
Controller 1 Code :-
app.controller('Ctrlone', ["$scope", "ServiceF", function ($scope, ServiceF) {
$scope.Info= {};
$scope.ser= function(){
ServiceF.sendData($scope.Info);
console.log($scope.Info);
};
}]);
The $scope.Info data is coming successfully here from other source which I haven't posted . But it is coming.
Controller 2 :-
app.controller('Ctrltwo', ["$scope" ,"ServiceF",
function($scope , ServiceF) {
$scope.Info= '';
$scope.$on('data_shared',function(){
var good = ServiceF.getData();
$scope.Info = good;
});
}]);
UI where I want to display info :-
<div class="col-sm-8">
<h1 class="mainTitle">Ok Start </h1>
<h2>{{good}}</h2>
</div>
Button click function from 1st UI :-
<label class="cardlabel" style="width:11vw" ui-sref="uitwo" ng-click="ser()">Send</label>
Now where am I going wrong ? Info is not displaying on 2nd UI. And how can I check if data is passing on Service ?
You have no attribute named good in your scope. So {{ good }} will always be empty.
The scope attribute is named Info. So you want {{ Info }}.

passing razor value into angular controller

I've looked at a half dozen examples, but none of them seems to work for me - maybe because of the peculiar var myController = [] format of the code I inherited.
.cshtml:
<div id="ng-app" ng-app="cmorApp">
<div
data-ng-controller="myCtrl"
data-ng-init="referralId = #Model.ReferralId">
...
This works, inasmuch as my page correctly renders the value I seek:
data-ng-init="referralId = 12345"
Now I'm just trying to capture it in my controller.
Controller:
var myCtrl = ['$scope', '$http', 'FileUploader',
function ($scope, $http, FileUploader, referralId) {
console.log(referralId);
//$scope.init = function (referralId) {
// console.log(referralId);
//}
//$scope.init();
It outputs undefined.
What am I missing?
.
UPDATE:
This sort of works:
ng-init="init(#Model.ReferralId)
.
$scope.init = function (referralId) {
$scope.referralId = referralId;
}
The problem is, the value is not there when I need it. It only there if I let the page do some processing.
I can't do this, or I'm back to undefined:
$scope.init = function (referralId) {
$scope.referralId = referralId;
}
console.log($scope.referralId);

AngularJS $interval and REST Calls

I've been struggling with getting $interval to work. So I was hoping everyone here could straighten me out. Here's my case..
I have a page, that contains a 'update' button. when that button is clicked it's calling a REST service to update a row in a table. On the backend we have a process that monitors that field and runs when it see's the value submitted. Once this process is done it changes the value to completed.
What I'm trying to do is once that button is clicked, a div will display with the status of 'Submitted'. then I want to use $interval to poll that field(via a REST call) and change my view once it's moved to a value of 'completed'. In short change the view from 'Submitted' to 'Completed'.
My problem is when the button is clicked, and I make my rest call if I set my 'data table' on the scope I get
TypeError: Cannot set property 'clst_rfrstatus_data_table' of
undefined
If I change it up and declare the data table like so
var refreshStatus_data_table = StatusService.getRefreshStatus().get({cluster: $stateParams.cluster});
refreshStatus_data_table.$promise.then(function (data) {
for (var x = 0; x < data.message.length; x++) {
$scope.refresh_status = (data.message[x].status == "null") ? data.message[x].status = "" : data.message[x].status;
$scope.$digest;
}
});
},3000);
..snip..
I get
ConsoleAgent: TypeError: Cannot set property 'refresh_status' of
undefined
I'm not following if I am not in scope or what.. Any help is
appreciated.
Code:
myapp-routes.js
myAppconfig(function ($stateProvider, $urlRouterProvider) {
'use strict';
$urlRouterProvider.otherwise('/home');
$stateProvider
.state('status_page', {
url: '/status_page/:cluster',
templateUrl: 'views/clusters/status_page.html',
controller: 'StatusController'
})
..snip..
Controller
clusterApp.controller('StatusController',['$scope','$interval','$state','$stateParams','StatusService', function ($scope, $interval, $state, $stateParams, StatusService) {
$scope.refresh_status = "";
$scope.ButtonClick = function ($scope) {
$scope.refreshStatus_data_table = StatusService.getRefreshStatus().get({cluster: $stateParams.cluster});
$interval( function(){
$scope.refreshStatus_data_table.$promise.then(function (data) {
for (var x = 0; x < data.message.length; x++) {
$scope.refresh_status = (data.message[x].status == "null") ? data.message[x].status = "" : data.message[x].status;
$scope.$digest;
}
});
},3000);
..snip..
} //end controller
view
<div>
<input type="button" value="Update" ng-click="ButtonClick()" />
Status: {{refresh_status}}
</div>
Your method header for ButtonClick expects you to pass in the $scope, but you are calling it without anything, so the local $scope variable is undefined in your method body. You shouldn't need to pass $scope though:
$scope.ButtonClick = function () {
...
}

Mixing onChange and ng-change in select

Ok, I know the following code is wrong since it's not working. But hopefully it'll help describe what I'm trying to do:
Choose a new background color for the site:
<select name="bgcolor" onChange="ModifyColorsInLess();" id="bgcolor" ng-change="changeCurrent('bgcurrent');">
<option ng-repeat="color in colorlist" value="{{color}}" ng-selected="color==bgcurrent" >{{color}}</option>
</select>
Now, you'll see I have two things that I want to happen on a selection.
1) Hit the JS function ModifyColorsInLess() which this does and does perfectly. The function is sitting in a regular JS file. This changes the actual value of a LESS variable immediately.
2) Hit the function in the controller of changeCurrent(). This is an attempt to change the value of a scope variable set in the Angular controller.
I'm trying to figure out how to make the code do both.
EDIT:
Controller code:
app.controller('HomeController', ['$scope', '$location', '$sce', '$routeParams', '$timeout', function($scope, $location, $sce, $routeParams, $timeout ) {
// Configuration Variables:
$scope.title = "Site Title";
$scope.logosrc = "images/site_logo.gif";
$scope.tagline = "This is the new tagline!!!";
$scope.bgcurrent = "White";
$scope.pccurrent = "Black";
$scope.sccurrent = "LightGray";
$scope.dtccurrent = "Black";
$scope.ltcurrent = "LightGray";
// This changes the shadowed aspect of the top nav and footer based on a checkbox
$scope.shadowChange = function(cb){
var isChecked = (document.getElementById('shadow').checked);
if(isChecked){
$('#footer').addClass('shadowed');
$('.nav').addClass('shadowed');
$('.show-menu').addClass('shadowed');
}else{
$('#footer').removeClass('shadowed');
$('.nav').removeClass('shadowed');
$('.show-menu').removeClass('shadowed');
};
return true;
};
// This converts any HTML code in the text to actual code so that it renders properly
$scope.renderHtml = function(html_code)
{
return $sce.trustAsHtml(html_code);
};
// This sets a default value for the passed parameter. $routeParams.action in this example
if(!(typeof $routeParams.action === 'undefined')){
$scope.pageAction = $routeParams.action;
}
else{
$scope.pageAction = "home";
}
// This changes a default color
$scope.changeCurrent = function(varname){
alert(varname);
// $scope[varname] = valname;
};
}]);

AngularJS extend Controller within controller

here's my issue: I want to run the code of controllerB into controllerA. The issue is that while the variables are returned to the controllerA, the values from requests are never returned. Here's a plunker to show the issue: http://plnkr.co/edit/GqC9BOKTi8HxQLf2a2yd?p=preview
var test = $scope.$new();
$controller('Ctrl1', {$scope : test});
//the first 2 lines are executed, but the 3d never returns a value
$scope.variable = test.variable;
$scope.varFromFunction = test.varFromFunction();
$scope.varFromRequest = test.varFromRequest;
The first 2 lines execute, but the 3d one never returns a value.
Since varFromRequest is located inside a $timeout method in the first controller with 500ms, it will execute 500s later meanwhile angular completes its linking phase.
Watching varFromRequest in the second controller is the easy solution
test.$watch('varFromRequest', function(new_value, old){
$scope.varFromRequest = test.varFromRequest;
})
Here is the updated plunker http://plnkr.co/edit/TqSjeckrdqeKquEbCwFX
The varFromFunction is undefined when the second controller tries to get a reference. The timeout sets this var after this request. If you delay the request for reference then you will get the appropriate value. This isn't the recommended way of working but it does answer your question why it hasn't been set yet.
myApp.controller('Ctrl1', ['$scope', '$timeout', function($scope, $timeout) {
$scope.variable = 'OH HAI';
$scope.varFromFunction = function(){
return "OH HAI FromFunction";
}
$timeout(function(){
$scope.varFromRequest = "time";
},500);
}]);
myApp.controller('Ctrl2', ['$scope', '$controller', '$timeout', function($scope, $controller, $timeout) {
var test = $scope.$new();
$controller('Ctrl1', {$scope : test});
$scope.variable = test.variable;
$scope.varFromFunction = test.varFromFunction();
$scope.varFromRequest = test.varFromRequest || 'unset';
$timeout(function(){
$scope.varFromRequest = test.varFromRequest || 'still unset';
},500);
}]);

Resources