Enter Your Email Address to Watch This Lesson

Your link to unlock this lesson will be sent to this email address.

Unlock this lesson and all 559 of the free egghead.io lessons, plus get Angular 1.x content delivered directly to your inbox!



Existing egghead members will not see this. Sign in.

Just one more step!

Check your inbox for an email from us and click link to unlock your lesson.



Sharing Data Between Controllers

5:13 Angular 1.x lesson by

If AngularJS Controllers are the glue of an application, how do they communicate and pass data around? This introduction to service factories will shed some light on that question.

Get the Code Now
click to level up

egghead.io comment guidelines

Avatar
egghead.io

If AngularJS Controllers are the glue of an application, how do they communicate and pass data around? This introduction to service factories will shed some light on that question.

Avatar
Mark

How would you use this approach with dynamic data?

I have data being added to a collection within the service factory using $http. I'm using one controller to initiate the request and than use $q.defer().resolve() to adjust its $scope, but the second controller that shares the same service doesn't update when the services data changes.

In reply to egghead.io
Avatar
Joel

I'd need to see the code but my guess is that you are completely overwriting the property with a new object. You want to update the object/array and not replace to allow binding to function.

In reply to Mark
Avatar
Elgs

These two controllers are in a parent-child relationship. How about sharing data between two side-by-side controllers?

Avatar
Abdo

To share the greeting service between the controllers, we used the variable name "greeting" in the controller's first argument. Does this not break after js minification? How can we work around this?

Avatar
Abdo

It does break the after minification. This is how you work around it:
.controller('FirstCtrl', ['greeting', function(foo) {
// foo is the greeting service in here
}])

In reply to Abdo
Avatar
John

Check out this lesson on using a build tool to make all your angular code "min safe".

https://egghead.io/lessons/angularjs-using-ng-annotate-for-min-safe-angularjs

In reply to Abdo
Avatar
arpan

What editor are you using?

Avatar
roberto

Hello there, i'm a bit new to Angular. So thank you for these courses :)

So here's a noob question. I'm trying to follow the lectures by also reading the Rout code module to have a deeper understanding:

https://code.angularjs.org/1.4.7/angular-route.js

Inside that code- I can't find: (1) ui-view or (2) ui- sref.

So Where are we getting those two functions from ?

Thanks !

Avatar
rui

I think what you should refer to is angular-ui-router rather than angular-router.

In reply to roberto
Avatar

Where can I find the code for this? The code below the video is not the one thats shown in the video

Avatar
Joel

Where can I find the code for this? The code below the video is not the one thats shown in the video

What you see is what you get!

In reply to
Avatar
mlaksv100

Is that deliberate? to post different version of code below the video?

In reply to Joel

Instead of using ngController on an element, it's actually preferred to use one controller per state. To use states we need to grab Angular UI routers. We'll copy it from a CDN and then simply paste it into our project.

To use UI router we need to add it to our list of dependencies, UI.router. Then, since we're going to be writing some more code, let's move this out to a separate script file. I'll cut this, create a new file called app.JS, and paste the code I had in there. Our application should still be working just fine.

To add a state for our controller we say, ".config" which allows us to configure our application before it boots up. We'll add a function called config which we're just naming for debugging later and add something called state provider, which is what we add our states to.

We'll say "stateprovider.state" and add a state of index. Now the second parameter here is a configuration object which takes a URL which will simply be nothing for now, a controller which will be first controller as first which should look familiar, first being how we will reference it in our HTML and first controller maps to the controller we created here, and then a template URL which is a template which we will load in.

We'll say, "templatesfirst.html." To create this template we'll switch over to our project view, create a new HTML file inside of the templates directory, and then I'll delete all this boiler plate code. We don't need that. Copy and paste all of this code, so cut it out and paste it in here.

Inside of our index we don't need this anymore, because that's referenced inside of our state and configured there. All we need is to say, "Use UI view," and place whatever template we've configured right on that UI view element and use the state provider to configure and provide that data.

Now our application is right back to where it was before, still working, but now our states are configured inside of a configure function and it's mapping a controller to a template where first controller is defined here and first is used inside of our template in each of those same positions.

This means that sharing data between controllers is essentially sharing data between states or templates. Let's create another template to pass some data into. We'll call this template second and just simply have it be an H1 with some binding in it that says second.greeting.message.

Now we need to create a state for this template by simply duplicating this line. We'll call this state second, give it a URL of second, rename this to second control, rename these guys to second. Then we need to create a second controller which we'll do by duplicating this and, again, renaming this to second and renaming these guys to second.

Now we have a second state with a second controller. To navigate to this URL in our first template, we'll just say div ui-sref which means, "Take us to this state when we click on it." We'll say, "Go to second." Now clicking on "go to second" will take us to a blank page because in our second template there's no data for this message.

To set this up and share data between controllers or states or templates or whatever you want to say, we'll create a service. We'll call this service greeting. We'll give it a named function of greeting. In this scenario this greeting is being treated like a constructor and returning an instance, so we're going to call it lower case. Some people call services upper case. It just depends on who you talk to, but we'll, for convenience, set up greeting as this in case of scoping issues later and say, "greeting.message equals default."

Now to share him between controllers, all we have to do is add him and here. We'll type greeting. Similarly for here and here instead of first we can say greeting. This gives us the same greeting object or service on each controller with a message property which we can bind to from each controller.

We already added message in our second template. Let's go ahead and do that in this first template. I'll find all the greetings and change it to greeting.message. Now if I run this and change it from default, again, it says default because the default message is default, if I change it to hi and click "go to second," you will see the message we get is hi.

HEY, QUICK QUESTION!
Joel's Head
Why are we asking?