3

I'm currently trying to build a component that will accept a model like this

      "values": {
        "value1": 234,
        "valueOptions": {
          "subOption1": 123,
          "subOption2": 133,
          "subOption3": 7432,
          "valueOptions2": {
            "subSubOption4": 821
          }
        }
      }  

with each object recursively creating a new component. So far I've created this branch and node components and its fine at receiving the data and displaying it but the problem I'm having is how I can edit and save the data. Each component has a different data set as it is passed down its own child object.

Js twiddle here : https://ember-twiddle.com/b7f8fa6b4c4336d40982

tree-branch component template:

{{#each children as |child|}}
{{child.name}} 
{{tree-node node=child.value}}
 {{/each}}

 {{#each items as |item|}}
  <li>{{input value=item.key}} : {{input value=item.value}} <button {{action 'save' item}}>Save</button></li>
{{/each}}

tree-branch component controller:

export default Ember.Component.extend({
tagName: 'li',
classNames: ['branch'],

items: function() {
    var node = this.get('node')

    var keys = Object.keys(node);

    return keys.filter(function(key) {
        return node[key].constructor !== Object
    }).map(function(key){
        return { key: key, value: node[key]};
    })

}.property('node'),

children : function() {

    var node = this.get('node');
    var children = [];
    var keys = Object.keys(node);

    var branchObjectKeys = keys.filter(function(key) {
        return node[key].constructor === Object
    })

    branchObjectKeys.forEach(function(keys) {
        children.push(keys)
    })

    children = children.map(function(key) {
        return {name:key, value: node[key]}
    })

    return children

    }.property('node'),


    actions:  {
        save: function(item) {
            console.log(item.key, item.value);
        }
    }

});

tree-node component:

{{tree-branch node=node}}

Anyone who has any ideas of how I can get this working would be a major help, thanks!

J T
  • 584
  • 1
  • 6
  • 10

2 Answers2

1

Use:

save(item) {
   let node = this.get('node');

   if (!node || !node.hasOwnProperty(item.key)) {
      return;
   }

   Ember.set(node, item.key, item.value);
}

See working demo.

Daniel Kmak
  • 18,164
  • 7
  • 66
  • 89
  • Is there anyway to save all the changes at once, rather than individually save actions? – J T Nov 16 '15 at 14:26
1

I think this would be the perfect place to use the action helper:

In your controller define the action:

//controller
actions: {
    save: function() {
        this.get('tree').save();
    }
}

and then pass it into your component:

{{tree-branch node=tree save=(action 'save')}}

You then pass this same action down into {{tree-branch}} and {{tree-node}} and trigger it like this:

this.attrs.save();

You can read more about actions in 2.0 here and here.

NicholasJohn16
  • 2,390
  • 2
  • 21
  • 45