3

I just give a try to AngularJS. I try to do something quite simple but I'd like to do it the good way.

I got a list of items in a table which displays name and quantity for each item. I have a form under the table.

When I click on an item name from the table I'd like the given item to be updatable through the form.

I achieve to do thing with scope inheritance as in fiddle http://jsfiddle.net/5cRte/1/

View :

<tr ng-repeat="item in items">
  <td><a href="#" ng-click="selectCurrentItem(item)">{{item.name}}</a></td>
  <td>{{item.quantity}}</td>
</tr>

Controllers :

function ItemListController($scope){
    $scope.items = [{name:'item1', quantity:10}, {name:'item2', quantity:5}];

    $scope.selectCurrentItem = function(currentItem) {
        $scope.currentItem = currentItem;
    }
}

function ItemFormController($scope){
    $scope.$watch('currentItem', function() {
        $scope.item = $scope.currentItem; 
    });
}

But has I read in some topics, it is not a good practice to couple controllers scopes this way, and preferably I'll wan't to use a service to store variables shared between controllers.

I was able to put a static variable in a service and retrieve it in another controller, but I can't make it updated when clicking on the item from the table, as watch not working on services variable. Have you an hint, for this ?

Thanks in advance

1 Answer 1

3

I don't know whether this is optimal but this what I could come up with

angular.module('myApp', []);

angular.module('myApp').factory('myService', function(){
    var items = [{name:'item1', quantity:10}, {name:'item2', quantity:5}, {name:'item3', quantity:50}];
    var current = {};
    return {
        getItems: function(){
            return items;
        },

        setCurrentItem: function(item){
            current.item = item;
        },

        removeCurrentItem: function(){
            delete current.item;
        },

        getCurrent: function(){
            return current;
        }
    }
});

function ItemListController($scope, myService){
    $scope.items = myService.getItems();

    $scope.selectCurrentItem = function(currentItem) {
        myService.setCurrentItem(currentItem);
    }
}

function ItemFormController($scope, myService){
    $scope.current = myService.getCurrent();
}

Demo: Fiddle

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

3 Comments

Hi, it comes to resolve what I was trying to do. I just can't figured out why it doesn't work if instead of getCurrent I have a getCurrentItem which then return current.item in the first place ?
@StephaneToussaint: because if you set current in ItemFormController's scope, it's watching current's changes (in this example by changing current.item). But if you set directly current.item to the scope, the scope cannot catch the changes, because technically, you set another object to variable but not in controller's scope (changing variable's reference is not supported in javascript). I hope the example can explain better: jsfiddle.net/q5BQt :)
Thank you for your comment. That indeed sounds obvious.

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.