Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/user-interface/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript Dojo中的事件处理_Javascript_Dojo - Fatal编程技术网

Javascript Dojo中的事件处理

Javascript Dojo中的事件处理,javascript,dojo,Javascript,Dojo,以Jeff Atwood为例,我决定为我正在编写的非常基本的待办事项列表应用程序使用JavaScript库。我选择了版本1.1.1。起初,一切都很好:我编写的拖放代码第一次起作用,您可以在屏幕上拖动任务以更改其优先顺序,并且每个拖放操作都调用一个事件处理程序,该事件处理程序向服务器发送一个AJAX调用,让服务器知道顺序已更改 然后我加入了电子邮件跟踪功能。标准材料:新收到的电子邮件在主题行上有一个唯一的ID号,所有后续关于该问题的电子邮件都可以通过在回复时将该ID号留在主题中来跟踪。因此,我们有

以Jeff Atwood为例,我决定为我正在编写的非常基本的待办事项列表应用程序使用JavaScript库。我选择了版本1.1.1。起初,一切都很好:我编写的拖放代码第一次起作用,您可以在屏幕上拖动任务以更改其优先顺序,并且每个拖放操作都调用一个事件处理程序,该事件处理程序向服务器发送一个AJAX调用,让服务器知道顺序已更改

然后我加入了电子邮件跟踪功能。标准材料:新收到的电子邮件在主题行上有一个唯一的ID号,所有后续关于该问题的电子邮件都可以通过在回复时将该ID号留在主题中来跟踪。因此,我们有一个打开的任务列表,每个任务都有自己的ID号,每个任务都有一个按时间顺序排列的关联电子邮件列表。我希望用户在查看任务列表时可以使用这些电子邮件的文本,因此我将每个任务框设置为Dijit“树”控件-顶层包含任务描述,分支包含电子邮件日期,每个分支的单个“叶子”包含电子邮件文本

第一个问题:我希望树视图在默认情况下完全折叠。在广泛搜索Google之后,我发现了许多解决方案,所有这些解决方案似乎都适用于Dojo的早期版本,但不是我正在使用的版本。我最终发现,最好的解决方案似乎是在加载树控件时调用一个事件处理程序,该事件处理程序可以简单地折叠每个分支/叶。不幸的是,即使树控件已经实例化并调用了它的“启动”事件处理程序,分支和叶子仍然没有加载(数据仍然是通过AJAX调用加载的)。因此,我修改了系统,以便所有电子邮件文本和树结构都添加到服务器端。这意味着在调用其启动事件处理程序时,整个完全填充的树控件都可用

因此,启动事件处理程序完全折叠树。接下来,我找不到一个“合适”的方法来为电子邮件页面提供格式良好的文本。我可以把电子邮件文本放在叶子上,但是任何HTML都会被转义出来并显示在网页上。更多的线索围绕Dojo的文档(往往已经过时,1.0之前版本的代码和示例)和Google进行搜索。我最终想出了一个解决方案,让JavaScript去读取每个叶节点内的SPAN元素,并在其innerHTML中取消转义转义HTML代码。我想我应该在树控件的启动事件处理程序中完全折叠树代码来完成这项工作

然而。。。事实证明,直到用户单击expando(树视图中单击以展开节点的小“+”符号)时,才真正创建SPAN元素。好的,很公平-我将把重新格式化的代码添加到onExpand()事件处理程序中,或者不管它叫什么。这似乎不存在。我搜索过文档,我搜索过谷歌。。。我很可能误解了Dojo的“发布/订阅”事件处理系统,但我认为这主要是因为似乎没有任何关于它的全面文档(比如,我在哪里可以找到我可以订阅的事件?)

因此,最后,我能想到的最佳解决方案是向每个树分支的expando节点添加一个onClick事件处理程序(不是“Dojo”事件,而是Dojo不知道的普通JavaScript事件),该节点在每个叶的SPAN元素内重新格式化HTML。除了当调用它时,SPAN元素仍然不存在(有时-有时它被缓存,只是为了进一步混淆)。因此,我让事件处理程序设置一个计时器,定期调用一个函数,在重新格式化之前检查相关的SPAN元素是否出现

// An event handler called whenever a "email title" tree node is expanded.
function formatTreeNode(nodeID) {
    if (dijit.byId(nodeID).getChildren().length != 0) {
        clearInterval(nodeUpdateIntervalID);
        messageBody = dijit.byId(nodeID).getChildren()[0].labelNode.innerHTML
        if (messageBody.indexOf("<b>Message text:</b>") == -1) {
            messageBody = messageBody.replace(/&gt;/g, ">");
            messageBody = messageBody.replace(/&lt;/g, "<");
            messageBody = messageBody.replace(/&amp;/g, "&");
            dijit.byId(nodeID).getChildren()[0].labelNode.innerHTML = "<b>Message text:</b><div style=\"font-family:courier\">"+messageBody+"</div>";
        }
    }
}

// An event handler called when a tree node has been set up - we changed the default fully-expanded to fully-collapsed.
function setupTree(theTree) {
    dijit.byId("tree-"+theTree).rootNode.collapse();

    messageNode = dijit.byId("tree-"+theTree).rootNode.getChildren();
    for (pl = 0; pl < messageNode.length; pl++) {
        messageNode[pl].collapse();
        messageNode[pl].expandoNode.onclick = eval("nodeUpdateIntervalID = setInterval(\"formatTreeNode('"+messageNode[pl].id+"')\",200); formatTreeNode('"+messageNode[pl].id+"');");
    }
}
//每当展开“电子邮件标题”树节点时调用事件处理程序。
函数formatTreeNode(nodeID){
if(dijit.byId(nodeID).getChildren().length!=0){
clearInterval(nodeUpdateIntervalID);
messageBody=dijit.byId(nodeID).getChildren()[0].labelNode.innerHTML
if(messageBody.indexOf(“消息文本:”)=-1){
messageBody=messageBody.replace(//g,“>”);

messageBody=messageBody.replace(//g,“我假设您遵循了指导您使用数据存储将数据传递到树控件的教程。这让我有一段时间头痛不已

这不是一个很好的方法,替代方法也没有很好的文档记录。您需要创建一个使用模型。我在下面提供了一个树模型的示例,该树模型是我为显示LDAP目录的结构而创建的

您将在dojo发行版的./dijit/_tree/model.js中找到该模型的默认实现。这些注释将帮助您理解该模型支持的功能

下面代码中的IDirectoryService类是(DWR)生成的服务器端Java POJO的存根。如果要进行大量的客户机-服务器交互,我强烈建议使用DWR

dojo.declare("LDAPDirectoryTreeModel", [ dijit.tree.model ], { getRoot : function(onItem) { IDirectoryService.getRoots( function(roots) { onItem(roots[0]) }); }, mayHaveChildren : function(item) { return true; }, getChildren : function(parentItem, onComplete) { IDirectoryService.getChildrenImpl(parentItem, onComplete); }, getIdentity : function(item) { return item.dn; }, getLabel : function(item) { return item.rdn; } }); declare(“LDAPDirectoryTreeModel”,[dijit.tree.model]{ getRoot:函数(onItem){ IDirectoryService.getRoots(函数(根){ (根[0]) }); }, mayHaveChildren:功能(项目){ 返回true; }, getChildren:函数(parentItem,onComplete){ IDirectoryService.getChildrenImpl(父项,onComplete); }, getIdentity:函数(项){ 返回item.dn; }, getLabel:函数(项){ 返回item.rdn; } }); 这里是我的JSP页面的摘录,我在这里创建了模型,并用它来填充树控件

<div dojoType="LDAPDirectoryTreeModel" jsid="treeModel" id="treeModel"> </div> <div jsid="tree" id="tree" dojoType="dijit.Tree" model="treeModel" labelAttr="name" label="${directory.host}:${directory.port}"> </div>