0

I guess it is best to describe it with a picture. I have an angular app and here is a simple view.

Basic view

Obvious explanation: list shows all the entities, if you click on an entity you can edit it in the form that is hidden by default and similar action applies to adding a new entity.

the issue

I know it is basic example so here the solution might be an overkill but I want to separate the logic of 'Add new entity', 'Edit entity' and 'Entities list'. I thought I could implement it like this:

<div ng-include="'userAddForm.html'"
     ng-show="???"
     ng-controller="AddUser as add">
</div>
<div ng-include="'userEditForm.html'"
     ng-show="???"
     ng-controller="AddEdit as edit">
</div>

<div class="panel panel-default">
   ... list managed by the current controller
</div>

What I miss

I have a difficulty in sharing a state of the hidden parts. For example some boolean flag. For instance:

  1. Click on the entity shows the edit form
  2. Save/Cancel in the edit form hides the part

Then, I think the first step is the responsibility of list-controller, but save/cancel part goes to edit-controller. It would be only possible to share the value with a service included in both - but that does not seem reasonable either.

I think there is some simple solution I can not see and I am open for any advice. Thanks!

3 Answers 3

1

If your goal is a simple solution with just a boolean being toggled in the model, you can use child controllers like this:

http://plnkr.co/edit/P1ncToJwqvxt9F9MTF5E?p=preview

The child controllers will inherit the scope of the parent controller and can directly edit the values. I have the edit child controller filtering for editMode==true, so when the parent changes that value, the child controller automatically shows the item. All changes are updated live and the child controller simply toggles the editMode property to remove it from the editing area.

Similar logic is used for the add child controller.

The views look like this:

index.html

<div ng-controller="myCtrl">

  <div ng-controller="addCtrl" ng-include="'userAddForm.html'">
  </div>
  <div ng-controller="editCtrl" ng-include="'userEditForm.html'">
  </div>
    <h1>Listing</h1>
    <ul>
        <li ng-repeat="item in items |  filter:{addMode:false}">
            {{item.id}}   
            {{item.name}}  

            <button ng-click="startEditing(item)">[ edit ]</button>
        </li>
    </ul>
    <button ng-click="startAdding()">[ add ]</button>
  <div>Debug:<br>{{items}}</div>
</div>

userAddForm.html

<ul>
    <li ng-repeat="item in items | filter:{addMode:true}">
        <input type="text" ng-model="item.id">
        <input type="text" ng-model="item.name">
          <button ng-click="add(item)">[ add ]</button>
          <button ng-click="cancel(item)">[ cancel ]</button>
    </li>
</ul>

userEditForm.html

<ul>
    <li ng-repeat="item in items | filter:{editMode:true}">
      <input type="text" ng-model="item.id">
      <input type="text" ng-model="item.name">
        <button ng-click="save(item)">[ save ]</button>
    </li>
</ul>

And the controllers look like this:

angular.module('myApp.controllers',[])
  .controller('addCtrl', function($scope) {
    $scope.add = function(item) {
      item.addMode = false;
    }
    $scope.cancel = function(item) {
      $scope.items.pop(item);
    }
  })
  .controller('editCtrl', function($scope) {
    $scope.save = function(item) {
      item.editMode = false;
    }
  })
  .controller('myCtrl', function($scope) {

        $scope.items = [
            {name:'aap', id:"1", editMode:false, addMode:false},    
            {name:'noot', id:"2", editMode:false, addMode:false},    
            {name:'mies', id:"3", editMode:false, addMode:false},    
            {name:'zus', id:"4", editMode:false, addMode:false}
        ];


        $scope.startAdding = function(){
          $scope.items.push({addMode:true});
        };

        $scope.startEditing = function(item){
          item.editMode = true;
        };

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

Comments

0

You can achieve this using Angular state routing.In which you will create state (different views) like -

header addEntity editEntity listEntity

refer https://github.com/angular-ui/ui-router/wiki/Nested-States-%26-Nested-Views

Comments

0

Sharing state can be implemented by creating a service which is than injected to all interested párties (controllers), service can hold data which controllers can be bound to and display in template. Services in Angular JS are singletons so all the controllers are accesing and mutating shared state.

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.