5

I like that AngularJS doesn't require and special syntax for Models, but there's one scenario I can't seem to wrap my head around. Take the following

My dataService wraps whatever flavor of data storage I'm using:

app.factory('dataService', function() {
    var data = 'Foo Bar';

    return {
        getData: function() {
            return data;
        }
    };
});

I have two controllers that both access the same piece of data:

app.controller('display', function($scope, dataService) {
    $scope.data = dataService.getData();
});

app.controller('editor', function($scope, dataService) {
    $scope.data = dataService.getData();
});

If I then have two views, one of which modifies the data, why doesn't the other update automatically?

<div ng-controller="display">
<p>{{data}}</p>
</div>

<div ng-controller="editor">
<input type="text" value="{{data}}"/>
</div>

I understand how this is working in something like Knockout where I'd be forced to make the data a knockout observable object. So any modifications in one part of the application trigger subscriptions and update views in another. But I'm not sure how to go about it in Angular.

Any advice?

3
  • 1
    if data is object scopes will share reference to same object, when data is primitive, they retain value independently Commented Apr 1, 2013 at 3:33
  • 2
    issue is not angular related, is the way javascript works jsfiddle.net/uGdEc Commented Apr 1, 2013 at 3:53
  • @charlietfl Exactly. When using a model layer like knockout does you're creating objects for everything that is meant to be observable. Remove that layer, and it doesn't seem to make sense how primitives could possibly be monitored (as your fiddle shows). Commented Apr 2, 2013 at 20:40

2 Answers 2

7

There are few changes that I would suggest to make it work.

  1. change the data object from a string to object type
  2. Use ng-model to bind the input field

HTML

<div ng-controller="display">
  <p>{{data.message}}</p>
</div>

<div ng-controller="editor">
  <input type="text" ng-model="data.message"/>
</div>

Script

app.factory('dataService', function() {
    var data = {message: 'Foo Bar'};

    return {
        getData: function() {
            return data;
        }
    };
});

Demo: Fiddle

Sign up to request clarification or add additional context in comments.

2 Comments

off-topic , related , can u pls see my q here
@RoyiNamir I'll have a loot at it... but I'm not a angular expert
1

I haven't been stuck with the same situation, but the thing that jumps out at me is what you are sticking in the scope. There was an angular video where scope was discussed. You should put model objects in the scope and not use the scope as your model object.

In your example two scopes will be created each with the string data. Since data is a string and immutable, it will be replaced in scope of editor when changed. In your example if you had dataService return an object and that object is shared between the controllers, then perhaps your problems would be resolved. Try having dataService return model of {data: data} and bind to model.data instead of data.

This is untested, but should work based on how I know angular works.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.