2013-12-17 43 views
0

我试图逐步加载节点树使用JSTree - 目前我有一个根节点基于它的一些路径与完整的数据和子节点的名称和路径他们。我需要在用户打开节点时更改其中的数据(加载完整数据)。这意味着我的JSON最初看起来像这样:在节点打开时逐步加载JSTree

{ 
"data":"Parent", 
"attr":{"id:":"103.510.1.4556314","name:":"Parent"}, 
"children":[{ 
    "data":"Child_1", 
    "attr":{"name":"Child_1","path":"/my/path/Child1"}, 
    "children":[] 
     }, 
     "data":"Child_2", 
    "attr":{"name":"Child_2","path":"/my/path/Child2"}, 
    "children":[] 
     }] 
} 

并且在打开Child_2时应该从源再次加载该节点的完整数据。此后,它应该例如像这样:

{ 
"data":"Parent", 
"attr":{"id:":"103.510.1.4556314","name:":"Parent"}, 
"children":[{ 
    "data":"Child_1", 
    "attr":{"name":"Child_1","path":"/my/path/Child1"}, 
    "children":[] 
     }, 
     "data":"Child_2", 
    "attr":{"name":"Child_2","id":"103.510.1.4523317"}, 
    "children":[{ 
     "data":"GrandChild_1", 
     "attr":{"name":"Child_1","path":"/my/path/Child2/GrandChild1"}, 
      "children":[] 
      }, 
      "data":"GrandChild_2", 
     "attr":{"name":"Child_2","path":"/my/path/Child2/GrandChild2"}, 
     "children":[] 
      }] 
     }] 
} 

我怎样才能实现这个功能吗?

这是我的Ajax调用:

function getJSONData(key) { 

    var test; 
    $.ajax({ 
     async: false, 
     type: "GET", 
     url: "/services/jstree?key=" + key, 
     dataType: "json", 

     success: function (json) { 
      test = json; 
     }, 

     error: function (xhr, ajaxOptions, thrownError) { 
      alert(xhr.status); 
      alert(thrownError); 
      test = "error"; 
     } 
    }); 
    return test; 
} 

在创建树它用于:

$(".tree-search").click(function() { 
    var jsonData = getJSONData($(this).attr("path")); 
    treeContainer = $(this).siblings('.tree-container'); 
    treeContent = treeContainer.children('.tree-content'); 
    treeContent.jstree({ 
     "json_data": {"data": jsonData}, 
     "plugins": ["themes", "json_data", "ui", "checkbox"] 
    }); 
}); 

谢谢你的建议!

+0

您可能想要设置一个jsFiddle,它包含HTML和样机Ajax请求,并包含您当前拥有的内容。 – Tomalak

+0

@Tomalak我几乎拥有实现我想要的代码所需的代码,因此我可能会跳过该代码并很快发布答案。尽管感谢您的关注! – Dropout

+0

我有几句话是相关的,但并不等于完整答案(因为如果没有看到更多的代码,这是不可能的)。无论如何。见下文。 – Tomalak

回答

1

我已经成功地让它做什么,我需要这种结合:

.bind("open_node.jstree", function (event, data) { 
       children = data.inst._get_children(data.rslt.obj); 
       for(var i=0; i<children.length; i++){ 
        data.inst.create_node(data.rslt.obj, "inside", getJSONData(children[i].getAttribute('path'))); 
        data.inst.delete_node(children[i]); 
       } 
      }); 

但它看起来像一个黑客,大概可以做一个更“干净”的方式更好。如果有人想出更好的答案,我会很乐意重新分配正确的答案。谢谢!

2

首先,你永远,永远从未使用async: false Ajax请求。此功能不存在。使用回调函数。

接下来,您不得在没有用var正确声明JavaScript变量的情况下使用JavaScript变量。忘记var会导致全局变量,这几乎总是可以归类为一个错误。

你可能想要事件委托,因为你的子树元素是动态创建的,并且仍然应该对相同的事件作出反应。

// read jQuery docs on Deferred to find out about fail() and done() etc. 
function getJSONData(key) { 
    return $.get("/services/jstree", {key: key}) 
     .fail(function (xhr, ajaxOptions, thrownError) { 
      alert(xhr.status + "\n" + thrownError); 
     }); 
    }); 
} 

// delegate "click" event handling to the document 
$(document).on("click", ".tree-search", function() { 
    var key = $(this).attr("path"); 

    getJSONData(key).done(function (jsonData) { 
     // call jstree() with jsonData 
    }); 
}); 
+0

感谢您提供的建议,我觉得它非常有用。然而,加载子程序的代码并不是我所需要的,但这可能是我没有足够清楚地说明我的问题的错。谢谢! – Dropout