2017-02-27 74 views
1

我嘗試使用組件在Vue中構建數據樹。正確輸出嵌套數組

考慮以下數據:

"data": [ 
{ 
    "id": 1, 
    "name": "foo", 
    "children": [ 
    { 
     "id": 2, 
     "name": "bar", 
     "children": [] 
    }, 
    { 
     "id": 3, 
     "name": "hulu", 
     "children": [] 
    } 
    ] 
}, 
{ 
    "id": 4, 
    "name": "foobar", 
    "children": [ 
    { 
     "id": 5, 
     "name": "foobar hulu", 
     "children": [] 
    } 
    ] 
}] 

現在我想與像一個表輸出它:

ID║名稱║路徑
1║FOO║/富
2║巴║/foo/bar
3║hulu║/ foo/hulu
4║foobar║/ foobar
5║foobar hulu║/ foo酒吧/ foobar hulu

我試過使用一個組件「調用」本身,如果有兒童可用。問題是Vue.js只允許一個根元素。

我的部件:

var Element = { 
    props: ['context', 'path'], 
    name: 'self', 
    template: ` 
     <tr> 
      <td>{{context.id}}</td> 
      <td>{{context.name}}</td> 
      <td>{{path}}</td> 
     </tr> 
     <self v-if="context.children.length != 0" v-for="child in context.children" :context="child" :path="path + '/' + child.name"></self> 
    ` 
}; 

var Tree = { 
    components: { 
     'element': Element 
    }, 
    template: ` 
     <table v-if="elements.length != 0"> 
      <thead> 
       <tr> 
        <th>ID</th> 
        <th>Name</th> 
        <th>Path</th> 
       </tr> 
      </thead> 

      <element v-for="element in elements" :context="element" :path="'/' + element.name"></element> 
     </table> 
    `, 

你如何繞過這個問題?我試過在tbody內包裝元素模板。這將正確計算路徑並輸出所有元素,但這會產生嵌套在列中的行,看起來非常難看。

enter image description here

任何想法?

回答

1

展平路徑。

Vue.component("flat-tree",{ 
    props:["paths"], 
    template: "#flat-tree-template", 
    methods:{ 
    flatten(data, root, accumulator){ 
     return data.reduce((acc, val) => { 
     accumulator.push({ 
      id: val.id, 
      name: val.name, 
      path: root + val.name 
     }); 
     if (val.children) 
      return this.flatten(val.children, root + val.name + "/", accumulator); 
     else 
      return accumulator; 
     }, accumulator); 
    } 
    }, 
    computed:{ 
    flattened(){ 
     return this.flatten(this.paths, "/", []); 
    } 
    } 
}) 

模板

<template id="flat-tree-template"> 
    <table> 
    <tr v-for="path in flattened"> 
     <td>{{path.id}}</td> 
     <td>{{path.name}}</td> 
     <td>{{path.path}}</td> 
    </tr> 
    </table> 
</template> 

Working example

+0

太棒了!不幸的是你的codepen不起作用,但我自己想出來了。爲什麼使用計算屬性輸出數據?是不是v-for =「flatten(paths,'/',[])」是相同的? – Qobus

+0

@Qobus我正在玩codepen一段時間,所以有可能你點擊鏈接,當它處於一個糟糕的狀態;道歉。它應該現在工作。我正在使用計算屬性,因爲展平路徑是從原始路徑派生的。通過使用計算,如果原始路徑改變,平坦路徑將被重新計算並反映新的狀態。 – Bert

+0

@Qobus通常它看起來更乾淨,至少對我來說。你是正確的,v-for =「平坦路徑(路徑,'/',[])」將完成幾乎相同的事情。 – Bert