Accessing scoped value from a Root Controller in AngularJS with UI Router - javascript

I have a simple requirement in which I need to display the value of $scope.resAVal on my index.html page. I have $scope.resAVal available in the RootCtrl.
index.html
<!DOCTYPE html>
<html ng-app="plunker">
<head>
<!-- required js libs and other stuff -->
</head>
<body>
<h3>{{resAVal}}</h3> <!-- This is what I need to display from RootCtrl -->
<div ui-view></div>
</body>
</html>
And here is the app.js:
var app = angular.module('plunker', ['ui.router']).
config(['$stateProvider', '$urlRouterProvider', '$locationProvider',
function($stateProvider, $urlRouterProvider, $locationProvider) {
$locationProvider.html5Mode(true);
$urlRouterProvider.otherwise('/');
$stateProvider
.state('home', {
url: '/',
resolve:{
resA: function(){
return {'value': 'A'};
}
},
views: {
'': {
templateUrl: 'home.html',
controller: 'RootCtrl'
},
'A#home': {
templateUrl: 'a.html',
controller: 'MainCtrl'
},
'B#home': {
templateUrl: 'b.html',
controller: 'MainCtrl'
},
'C#home': {
templateUrl: 'c.html',
controller: 'MainCtrl'
}
}
});
}
]);
app.controller('RootCtrl', function($scope, resA) {
$scope.bar = [];
$scope.resAVal = resA.value;
})
app.controller('MainCtrl', function($scope) {
var fruits = [{"name": "Apple"}, {"name": "Banana"}, {"name": "Carrot"}];
$scope.foo = 2;
$scope.$watch('foo', function(value, oldValue) {
$scope.bar.length = 0; //correct
getBar(fruits, value);
});
function getBar(fruits, howManyFruits) {
for (var i = 0; i < $scope.foo; i++) {
$scope.bar.push(fruits[i]);
}
}
});
Here is the plunker for it.
Could somebody help me with it?

Any reason why you couldn't move the {{resAVal}} into the home.html view?
<h3>{{resAVal}}</h3>
<div class="row">
<div ui-view="A"></div>
<div ui-view="B"></div>
<div ui-view="C"></div>
</div>
If you really can't do this, you can always inject the rootScope in your root controller:
app.controller('RootCtrl', function($scope, $rootScope, resA) {
$scope.bar = [];
$scope.resAVal = resA.value;
$rootScope.resAVal = resA.value;
})

Your problem is with $scope
If you declared $rootScope.resAVal it is working fine
Plunkr Here

Related

separating viewroute.js file from angularjs does not load

I am able to run this code without separating. But when I seperate it ceases to run without any error on console. Also in separate viewroute.js I am able to hit debugger but not able to load normal behavior. I am doing some conceptual error as I am facing issues in separating services from same code as well. Please advise. Tried loading jquery before angularjs as well
By Default localhost address is :- http://localhost:3000/#!/
folder structure is as follows:-
public> 1. controllers>1. membershipcontroller
2. mgRoute > viewroute.js
views- index.html
Index.html file is as follows, this contains order of scripts being loaded:-
<!DOCTYPE html>
<html ng-app="tdmModule">
<head>
<title>welcome</title>
<!-- Bootstrap core CSS -->
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.4/angular.min.js">
</script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.4/angular-
route.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.6.4/angular-
resource.js"></script>
<script src="vendor/jquery/jquery.min.js"></script>
<script src="vendor/bootstrap/js/bootstrap.bundle.min.js"></script>
<script src="ngRoute/viewroute.js" type="text/javascript"></script>
<script src="controllers/app.js" type="text/javascript"></script>
<link href="vendor/bootstrap/css/bootstrap.min.css" rel="stylesheet">
<link href="stylesheets/style.css" rel="stylesheet">
</head>
<body>
<div>
<div class="container pt-5">
<div ng-view></div>
</div>
</div>
</body>
</html>
My app.js file is as follows:-
var app = angular.module("tdmModule", ["ngRoute"]);
app.config(['$qProvider', function($qProvider) {
$qProvider.errorOnUnhandledRejections(false);
}]);
//I WANT TO SEPERATE THIS FILE FROM HERE TO A SEPERATE FILE
app.config(['$routeProvider', '$locationProvider',
function($routeProvider, $locationProvider) {
$routeProvider
.when("/", {
templateUrl: "home",
controller: 'homeController'
})
.when("/membershipdetails", {
templateUrl: "membershipdetails",
controller: 'membershipController'
})
.when("/help", {
templateUrl: "help",
controller: 'helpController'
}).otherwise({
redirectTo: '/'
});
}
]);
// TILL HERE
app.controller('membershipController', function($scope, $filter, $http,
$httpParamSerializer, $location, membershipService, setnotanoption,
compileservice) {
var absurl = $location.absUrl().split('/#!/')[1];
$scope.pagename = absurl;
$scope.noOfColumn = false;
$scope.currentPage = 0;
$scope.pageSize = 5;
$scope.q = '';
$scope.selectColumnList = [];
$scope.tableBody = [];
$scope.columnResponse = [];
$scope.output = [];
$scope.inputjson = '';
$scope.NoOfRecords = '';
$scope.enviornmentOptions = [{
name: "Select a Enviornment",
id: 1
}, {
name: "BOSSBR03",
id: 2
}, {
name: "BOSST03",
id: 3
}];
$scope.selectedEnvOption = $scope.enviornmentOptions[0];
$scope.nextData = function() {
return $filter('filter')($scope.tableBody, $scope.q)
}
$scope.numberOfPages = function() {
return Math.ceil($scope.nextData().length / $scope.pageSize);
}
$scope.isObjectEmpty = function(card) {
return Object.keys(card).length === 0;
}
$('#fetchDetail').on('click', function() {
$scope.selectColumnList = [];
$("#rightColumn option").each(function(index) {
$scope.selectColumnList[index] = $(this).text();
});
if ($scope.selectColumnList.length > 3) {
$("#columnSelectionModel").modal('hide');
} else {
$scope.$apply(function() {
$scope.noOfColumn = true;
});
}
});
});
What I tried is the following file:- viewroute.js.
I am able to hit debugger that implies it is being loaded. but when i comment it out from app.js file. My page does not get loaded. Doesn't throw an error as well in console.
var app = angular.module("tdmModule", ["ngRoute"]);
//for Possibly unhandled rejection
app.config(['$qProvider', function($qProvider) {
$qProvider.errorOnUnhandledRejections(false);
}]);
debugger; ///this debugger is being hit
app.config(function($routeProvider) {
$routeProvider
.when("/", {
templateUrl: "home",
controller: 'homeController'
})
.when("/membershipdetails", {
templateUrl: "membershipdetails",
controller: 'membershipController'
})
.when("/help", {
templateUrl: "help",
controller: 'helpController'
}).otherwise({
redirectTo: '/'
});
});
Seems like you are declaring the tdmModule twice.
You can follow two path:
Declaring your routes as part of the tdmModule
In this way your viewroutes.js will looks like:
var app = angular.module("tdmModule");
app.config(function($routeProvider) {
$routeProvider
.when("/", {
templateUrl: "home",
controller: 'homeController'
})
.when("/membershipdetails", {
templateUrl: "membershipdetails",
controller: 'membershipController'
})
.when("/help", {
templateUrl: "help",
controller: 'helpController'
})
.otherwise({
redirectTo: '/'
});
});
Declaring your routes as part of a new module, a routesModule, as dependency of your tdmModule.
In this way your viewroutes.js will looks like:
var app = angular.module("routesModule", ["ngRoute"]);
app.config(function($routeProvider) {
$routeProvider
.when("/", {
templateUrl: "home",
controller: 'homeController'
})
.when("/membershipdetails", {
templateUrl: "membershipdetails",
controller: 'membershipController'
})
.when("/help", {
templateUrl: "help",
controller: 'helpController'
})
.otherwise({
redirectTo: '/'
});
});
And your app.js should be:
var app = angular.module("tdmModule", ["routesModule"]);
...
Hope it helps.
Edited
First option doesn't work in your case because of the order of your scripts.
Order is important, you have to declare the tdmModule before defining a config on it.
So you have to place controller/app.js import before viewroutes.js.

Update $state variable in 1 module from another

https://plnkr.co/edit/PWuKuVw9Dn9UJy6l8hZv?p=preview
I have 3 modules, routerApp, tickers and tags. Basically trying to rebuild my app out of smaller mini-apps.
The routerApp template contains the 2 directives for the other modules.
Expected
When you login, then click on the Count button in the tickers.component, I want to send the counter var into the tags.component $scope via $state.go.
Result
Nothing happens. No $state/variable update in the tags.component
Plnkr app.js code:
// TICKERS app module
var tickers = angular.module('tickers', ['ui.router'])
tickers.config(function($stateProvider) {
const tickers = {
name: 'tickers',
url: '/tickers',
parent: 'dashboard',
templateUrl: 'tickers-list.html',
bindToController: true,
controllerAs: 'tik',
controller: function() {
}
}
$stateProvider
.state(tickers);
})
tickers.component('tickersModule', {
templateUrl: 'tickers-list.html',
controller: function($scope, $state) {
console.log('Tickers init')
$scope.counter = 0;
$scope.increase = function() {
$scope.counter++;
console.log('increase', $scope.counter)
$state.go('dashboard.tags', { counter: $scope.counter });
}
}
})
// TAGS app module
var tags = angular.module('tags', ['ui.router'])
tags.config(function($stateProvider) {
const tags = {
name: 'tags',
url: '/tags?counter',
parent: 'dashboard',
params: {
counter: 0
},
templateUrl: 'tags-list.html',
bindToController: true,
controllerAs: 'tags',
controller: function($state) {
}
}
$stateProvider
.state(tags);
})
tags.component('tagsModule', {
templateUrl: 'tags-list.html',
controller: function($scope, $state) {
// Expecting this to update:
console.log('Tags init', $state)
$scope.counter = $state.params.counter;
}
})
// MAIN ROUTERAPP module
var routerApp = angular.module('routerApp', ['ui.router', 'tickers', 'tags']);
routerApp.config(function($stateProvider, $urlRouterProvider) {
$urlRouterProvider.otherwise('/login');
const login = {
name: 'login',
url: '/login',
templateUrl: 'login.html',
bindToController: true,
controllerAs: 'l',
controller: function($state) {
this.login = function() {
$state.go('dashboard', {})
}
}
}
const dashboard = {
name: 'dashboard',
url: '/dashboard',
templateUrl: 'dashboard.html',
controller: function() {
}
}
$stateProvider
.state(login)
.state(dashboard);
})
dashboard.html
<div class="jumbotron text-center">
<h1>The Dashboard</h1>
</div>
<div class="row">
<tickers-module></tickers-module>
<tags-module></tags-module>
</div>
The function in the tickers component that is trying to update the $state of the tags component:
$scope.increase = function() {
$scope.counter++;
console.log('increase', $scope.counter)
$state.go('dashboard.tags', { counter: $scope.counter });
}
Also tried: $state.go('tags', { counter: $scope.counter });
Finally the tags.component.
Note that here I'm not seeing the $scope.counter update nor the controller for the component getting refreshed due to a state change.
tags.component('tagsModule', {
templateUrl: 'tags-list.html',
controller: function($scope, $state) {
console.log('Tags init', $state)
$scope.counter = $state.params.counter;
}
})
Is the way I am architecting this going to work? What am I missing?
Update: Added some $rootScope events to watch for $state changes, hope this helps:
This is after clicking the login button and going from the login state to the dashboard state, but still nothing for clicking on the Count button.
So, it looks like you're properly passing the parameters in your $state.go call.
I think the issue here is that you're not properly handling the state parameters you're passing from the tickers component to the tags component.
Try injecting $stateParams into your tags component and pull the parameters off that object, for example (in your tags controller):
$scope.counter = $stateParams.counter;
Figured it out!
https://plnkr.co/edit/CvJLXKYh8Yf5npNa2mUh?p=preview
My problem was that in the $state object tags, I was using the same template as the tags.component.
Instead I needed to change it to something like <p>{{ counter }}</p>
var tags = angular.module('tags', ['ui.router'])
tags.config(function($stateProvider) {
const tags = {
name: 'tags',
url: '/tags',
parent: 'dashboard',
params: {
counter: 0
},
template: '<p>{{ counter }}</p>',
bindToController: true,
controller: function($scope, $state) {
console.log('tags state object', $state)
$scope.counter = $state.params.counter;
}
}
$stateProvider
.state(tags);
})
tags.component('tagsModule', {
templateUrl: 'tags-module-template.html',
controller: function($scope, $state) {
}
})
Then in my tags-module.template.html I needed to add a <div ui-view></div>
<div class="jumbotron text-center">
<h2>Tags list</h2>
<div ui-view></div> // <- here and this is where the $state object updates
{{ counter }}
</div>

I'm not seeing ng-repeat data on browser Angular js

For some reason I'm not visualizing data in the browser.
Here a pic of my console:
Inside p tag I am expecting to see retrieved data.
Here is the view:
<div class="row" ng-repeat="voce in voices">
<p style="color:#000;">{{voce.series}}</p>
</div>
Here is the controller:
app.controller('MainCtrl', function($scope,$q,voci) {
var promise = voci.getVoices();
promise.then(function(data){
$scope.voices = data;
console.log($scope.voices);
});
});
Here is the service voci:
app.service('voci', function ($http,$q) {
var deferred = $q.defer();
$http.get('urldata.json').then(function(data)
{
deferred.resolve(data);
});
this.getVoices = function(){
return deferred.promise;
};
})
Output of console.log $scope.voices:
I am using ngroute to associate views and controller, in the main module:
var app = angular.module('generaPreventivoApp', [
'ngAnimate',
'ngCookies',
'ngResource',
'ngRoute',
'ngSanitize'
])
.config(function ($routeProvider, $locationProvider) {
$routeProvider
.when('/', {
templateUrl: 'views/main.html',
controller: 'MainCtrl',
controllerAs: 'main'
})
.when('/about', {
templateUrl: 'views/about.html',
controller: 'AboutCtrl',
controllerAs: 'about'
})
.otherwise({
redirectTo: '/'
});
$locationProvider.hashPrefix('');
});
Why this kind of problem? Thank you
try with:
<div class="row" ng-repeat="voce in voices.data">
<p style="color:#000;">{{voce.series}}</p>
</div>
or:
app.controller('MainCtrl', function($scope,$q,voci) {
var promise = voci.getVoices();
promise.then(function(data){
$scope.voices = data.data;
console.log($scope.voices);
});
});

AngularFire browser Refresh gives error page not Found

Scenario is,
Im new to AngularJS and making an AngularJS with AngularFire, I have defined my routing bye using $routeProvider ,see below
var appMainModule = angular.module('appMain', [ 'firebase','ngRoute'])
.config(function ($routeProvider, $locationProvider) {
$routeProvider.when('/', { templateUrl: '/Templates/CustomerLogin.html', controller: 'HomeCtrl' });
$routeProvider.when('/customer/home', { templateUrl: '/Templates/CustomerHome.html' , controller:'ForLogout'});
$routeProvider.when('/customer/singup', { templateUrl: '/Templates/CustomerSinup.html', controller: 'RegisterCtrl' });
$routeProvider.when('/dashboard/godash', { templateUrl: '/Templates/dashboard.html', controller: 'DashboardCtrl' });
$routeProvider.when('/customer/list', { templateUrl: '/Templates/CustomerList.html', controller: 'customerListViewModel' });
$routeProvider.when('/customer/detail', { templateUrl: '/Templates/CustomerDetail.html', controller: 'customerDetailViewModel' });
$routeProvider.when('/customer/googlemap', { templateUrl: '/Templates/GoogleMap.html', controller: 'MapCtrl' });
// $routeProvider.when('/customer/postdata', { templateUrl: '/Templates/CustomerPostData.html', controller: 'AddPostCtrl' });
$routeProvider.when('/customer/getdata', { templateUrl: '/Templates/CustomerGetData.html', controller: 'GetCtrl', reloadOnSearch: false });
$routeProvider.when('/victim/getdata', { templateUrl: '/Templates/RiskVictimDetail.html', controller: 'VictimGetCtrl' });
$routeProvider.otherwise({ redirectTo: '/' });
$locationProvider.html5Mode(true);
});
this is my login controller
appMainModule.controller('HomeCtrl', ['$scope', '$location', 'CommonProp', '$firebaseAuth', function ($scope, $location,CommonProp, $firebaseAuth) {
var firebaseObj = new Firebase("FireaseURL/");
loginObj = $firebaseAuth(firebaseObj);
$scope.user = {};
var login = {};
$scope.SignIn = function (e) {
login.loading = true;
e.preventDefault();
var username = $scope.user.email;
var password = $scope.user.password;
loginObj.$authWithPassword({
email: username,
password: password
})
.then(function (user) {
//Success callback
// alert('Authentication successful');
login.loading = false;
$location.path('/dashboard/godash')
}, function (error) {
//Failure callback
alert('Authentication failure');
});
}
}])
my problem is that, when I refresh my login page by browser refresh, it refreshes successfully, but after login when refresh any page it gives me error
Page Not Found
my HTML:
<!DOCTYPE html>
<html data-ng-app="sampleApp">
<head>
<title>My new Project</title>
<meta charset="utf-8" />
<!-- AngularJS -->
<script src="Scripts/angular.min.js"></script>
<script src="Scripts/angular-route.min.js"></script>
<!-- Firebase -->
<script src="https://cdn.firebase.com/js/client/2.2.4/firebase.js"></script>
<!-- AngularFire -->
<script src="https://cdn.firebase.com/libs/angularfire/1.2.0/angularfire.min.js"></script>
<script src="Scripts/App.js"></script>
<base href="/" />
</head>
<body ng-view>
</body>
</html>
If you configure $location to use html5Mode (history.pushState), you need to specify the base URL for the application with a <base href=""> tag or configure $locationProvider to not require a base tag by passing a definition object with requireBase:false to $locationProvider.html5Mode():
$locationProvider.html5Mode({
enabled: true,
requireBase: false
});
From : https://docs.angularjs.org/error/$location/nobase
Be sure to check all relative links, images, scripts etc. Angular requires you to specify the url base in the head of your main html file () unless html5Mode.requireBase is set to false in the html5Mode definition object passed to $locationProvider.html5Mode(). With that, relative urls will always be resolved to this base url, even if the initial url of the document was different.
From : https://code.angularjs.org/1.3.14/docs/guide/$location
Simple example:
Index.html
<!DOCTYPE html>
<html data-ng-app="appMain">
<head>
<meta charset="utf-8" />
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.2.25/angular.min.js"></script>
<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.2.25/angular-route.js"></script>
<script src="script.js"></script>
<base href="/" />
</head>
<body ng-view>
</body>
</html>
script.js
var appMainModule = angular.module('appMain', ['ngRoute'])
.config(function($routeProvider, $locationProvider) {
$routeProvider.when('/', {
templateUrl: '/Templates/CustomerLogin.html',
controller: 'HomeCtrl'
});
$routeProvider.when('/customer/home', {
templateUrl: '/Templates/CustomerHome.html',
controller: 'ForLogout'
});
$routeProvider.when('/dashboard/godash', {
templateUrl: '/Templates/dashboard.html',
controller: 'DashboardCtrl'
});
$routeProvider.otherwise({
redirectTo: '/'
});
$locationProvider.html5Mode(true);
});
appMainModule.controller('HomeCtrl', ['$scope', '$location', function($scope, $location) {
$scope.godash = function(e) {
$location.path('/dashboard/godash')
}
}]);
appMainModule.controller('DashboardCtrl', ['$scope', '$location', function($scope, $location) {
$scope.home = function(e) {
$location.path('/customer/home')
}
}]);
appMainModule.controller('ForLogout', ['$scope', '$location', function($scope, $location) {
$scope.home = function(e) {
$location.path('/')
}
}]);
/Templates/CustomerLogin.html
<div>
<button ng-click="godash()">/dashboard/godash</button>
</div>
/Templates/CustomerHome.html
<div>
<button ng-click="home()">/</button>
</div>
/Templates/dashboard.html
<div>
<button ng-click="home()">/customer/home</button>
</div>

Loading URL into ng-view programatically

Referring to the code given below, I would like to be able to load viewTeam URL into ng-view from the showTeam() function. How can I do this?
<html>
<head>
<script src = "https://ajax.googleapis.com/ajax/libs/angularjs/1.4.9/angular.min.js"></script>
<script src = "https://ajax.googleapis.com/ajax/libs/angularjs/1.4.9/angular-route.min.js"></script>
<script>
var teamApp = angular.module("teamApp", ['ngRoute']);
teamApp.controller('teamController', function($scope, $http) {
$http
.get('/teams')
.success(function(response) {
$scope.teams = response;
}
);
var showTeam = function(id) {
}
});
teamApp.config(['$routeProvider', function($routeProvider) {
$routeProvider.
when('/addTeam', {
templateUrl: 'addTeam.htm',
controller: 'AddTeamController'
}).
when('/viewTeam', {
templateUrl: 'viewTeam.htm',
controller: 'ViewTeamController'
}).
otherwise({
redirectTo: '/addTeam'
});
}]);
teamApp.controller('AddTeamController', function($scope) {
});
teamApp.controller('ViewTeamController', function($scope, $routeParams) {
});
</script>
</head>
<body>
<div ng-app = "teamApp" ng-controller="teamController">
<button ng-click="newTeam()">new</button>
<div ng-repeat="team in teams" >
Name: {{team.name}}
<br />
Description: {{team.description}}
<br />
<button ng-click="showTeam(team.id)">show</button>
</div>
<div ng-view></div>
<script type = "text/ng-template" id = "addTeam.htm">
<h2> Add Team </h2>
To be implemented later.
</script>
<script type = "text/ng-template" id = "viewTeam.htm">
Name: {{team.name}}
Description: {{team.description}}
</script>
</div>
</body>
</html>
You need to change your $routeprovider for viewTeam to expect an id parameter. Then get that id in the viewTeamController using routeparams. Here is how you do it. Just follow the pattern in the script below:
<script>
var teamApp = angular.module("teamApp", ['ngRoute']);
teamApp.controller('teamController', function($scope, $http,$location) {
$http
.get('/teams')
.success(function(response) {
$scope.teams = response;
}
);
var showTeam = function(id) {
$location.url("#/viewTeam/" + id);//there are other means as well.
}
});
teamApp.config(['$routeProvider', function($routeProvider) {
$routeProvider.
when('/addTeam', {
templateUrl: 'addTeam.htm',
controller: 'AddTeamController'
}).
when('/viewTeam/:id', {
templateUrl: 'viewTeam.htm',
controller: 'ViewTeamController'
}).
otherwise({
redirectTo: '/addTeam'
});
}]);
teamApp.controller('AddTeamController', function($scope) {
});
teamApp.controller('ViewTeamController', function($scope, $routeParams) {
alert($routeParams.id);//you get the route params here.
});
</script>
When navigating from view:
<a href="#viewTeam/45">
In your case:
<a href="#viewTeam/{{team.id}}"> //to navigate from view.
In your teamController do this -
var showTeam = function(id) {
$location.path('/viewTeam.htm').search({'id': id});
}
In ViewTeamController you can get id like this
//Get id from url params
$location.search('id');
you can use $location to change the path
$scope.showTeam = function(view){
$location.path("/viewTeam"); // path not hash
}

Categories

Resources