tree.html 2.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127
  1. <script src="../../dist/vue.global.js"></script>
  2. <!-- item template -->
  3. <script type="text/x-template" id="item-template">
  4. <li>
  5. <div
  6. :class="{bold: isFolder}"
  7. @click="toggle"
  8. @dblclick="changeType">
  9. {{model.name}}
  10. <span v-if="isFolder">[{{open ? '-' : '+'}}]</span>
  11. </div>
  12. <ul v-show="open" v-if="isFolder">
  13. <tree-item
  14. class="item"
  15. v-for="model in model.children"
  16. :model="model">
  17. </tree-item>
  18. <li class="add" @click="addChild">+</li>
  19. </ul>
  20. </li>
  21. </script>
  22. <!-- item script -->
  23. <script>
  24. const TreeItem = {
  25. name: 'TreeItem', // necessary for self-reference
  26. template: '#item-template',
  27. props: {
  28. model: Object
  29. },
  30. data() {
  31. return {
  32. open: false
  33. }
  34. },
  35. computed: {
  36. isFolder() {
  37. return this.model.children &&
  38. this.model.children.length
  39. }
  40. },
  41. methods: {
  42. toggle() {
  43. if (this.isFolder) {
  44. this.open = !this.open
  45. }
  46. },
  47. changeType() {
  48. if (!this.isFolder) {
  49. this.model.children = []
  50. this.addChild()
  51. this.open = true
  52. }
  53. },
  54. addChild() {
  55. this.model.children.push({
  56. name: 'new stuff'
  57. })
  58. }
  59. }
  60. }
  61. </script>
  62. <p>(You can double click on an item to turn it into a folder.)</p>
  63. <!-- the app root element -->
  64. <ul id="demo">
  65. <tree-item class="item" :model="treeData"></tree-item>
  66. </ul>
  67. <script>
  68. const treeData = {
  69. name: 'My Tree',
  70. children: [
  71. { name: 'hello' },
  72. { name: 'wat' },
  73. {
  74. name: 'child folder',
  75. children: [
  76. {
  77. name: 'child folder',
  78. children: [
  79. { name: 'hello' },
  80. { name: 'wat' }
  81. ]
  82. },
  83. { name: 'hello' },
  84. { name: 'wat' },
  85. {
  86. name: 'child folder',
  87. children: [
  88. { name: 'hello' },
  89. { name: 'wat' }
  90. ]
  91. }
  92. ]
  93. }
  94. ]
  95. }
  96. Vue.createApp({
  97. components: {
  98. TreeItem
  99. },
  100. data: () => ({
  101. treeData
  102. })
  103. }).mount('#demo')
  104. </script>
  105. <style>
  106. body {
  107. font-family: Menlo, Consolas, monospace;
  108. color: #444;
  109. }
  110. .item {
  111. cursor: pointer;
  112. }
  113. .bold {
  114. font-weight: bold;
  115. }
  116. ul {
  117. padding-left: 1em;
  118. line-height: 1.5em;
  119. list-style-type: dot;
  120. }
  121. </style>