`

给树加上右键菜单,及实现菜单相应功能

 
阅读更多

15.4  给树加上右键菜单,及实现菜单相应功能

本节实例的效果如图15.5所示。给TreeViewer加右键菜单的方法和TableViewer相似,也要用到Action、ActionGroup、MenuManager类,当然程序要根据树的特点稍做改动。

图15.5  右键菜单效果图

(1)在15.3节主程序的tv.setInput(input)之后插入如下两句:

//--------------完整代码见文件:TreeViewer2.java--------------

MyActionGroup actionGroup = new MyActionGroup(tv);// 生成一个ActionGroup对象

actionGroup.fillContextMenu(new MenuManager());// 将按钮注入到菜单对象中

(2)创建MyActionGroup类,其代码如下所示。MyActionGroup内含各Action类,在实现Action时,对传入的结点对象要记得进行空值判断,因为TreeViewer的大部分方法都不支持空值参数,会导致异常并中断程序。

public class MyActionGroup extends ActionGroup {

         private TreeViewer tv;

         public MyActionGroup(TreeViewer treeViewer) {

                   this.tv = treeViewer;

         }

         // 生成菜单Menu,并将两个Action传入

         public void fillContextMenu(IMenuManager mgr) {

                   // 加入两个Action对象到菜单管理器

                   MenuManager menuManager = (MenuManager) mgr; // 类型转换

                   menuManager.add(new OpenAction());

                   menuManager.add(new RefreshAction());

                   menuManager.add(new ExpandAction());

                   menuManager.add(new CollapseAction());

                   menuManager.add(new AddEntryAction());

                   menuManager.add(new RemoveEntryAction());

                   menuManager.add(new ModifyEntryAction());

                   // 生成Menu并挂在树Tree上

                   Tree tree = tv.getTree();

                   Menu menu = menuManager.createContextMenu(tree);

                   tree.setMenu(menu);

         }

         // “打开”的Action类

         private class OpenAction extends Action {

                   public OpenAction() {

                            setText("打开");

                   }

                   public void run() {

                            ITreeEntry entry = getSelTreeEntry();

                            if (entry != null)

                                     MessageDialog.openInformation(null, null, entry.getName());

                   }

         }

         // 刷新的Action类

         private class RefreshAction extends Action {

                   public RefreshAction() {

                            setText("刷新");

                   }

                   // 如果在删除结点时,不同时从数据模型里删除结点。则执行本刷新后,该结点又会从

                   // 数据模型中取出并显示在界面上

                   public void run() {

                            tv.refresh();

                   }

         }

         // 展开当前结点的Action类

         private class ExpandAction extends Action {

                   public ExpandAction() {

                            setText("展开");

                   }

                   public void run() {

                            ITreeEntry entry = getSelTreeEntry();

                            if (entry != null)

                                     tv.expandToLevel(entry, 1); // 参数2是展开的层数

                   }

         }

         // 收缩当前结点的Action类

         private class CollapseAction extends Action {

                   public CollapseAction() {

                            setText("收缩");

                   }

                   public void run() {

                            ITreeEntry entry = getSelTreeEntry();

                            if (entry != null)

                                     tv.collapseToLevel(entry, -1); // 参数2是收缩的层数,-1指收缩所有子结点

                   }

         }

         // 给当前结点增加一个子结点的Action类

         private class AddEntryAction extends Action {

                   public AddEntryAction() {

                            setText("增加");

                   }

                   public void run() {

                            ITreeEntry entry = getSelTreeEntry();

                            if (entry == null || entry instanceof PeopleEntity)

                                     return;// 不能给“人”结点增加子结点

                            InputDialog dialog = new InputDialog(null, "增加子结点", "输入名称:", "a", null);

                            if (dialog.open() == InputDialog.OK) {// 如果单击OK按钮

                                     String entryName = dialog.getValue(); // 得到Dialog输入值

                                     // 根据单击结点的不同类型生成相应的子结点

                                     ITreeEntry newEntry = null;

                                     if (entry instanceof CountryEntity)

                                               newEntry = new CityEntity(entryName);

                                     else if (entry instanceof CityEntity)

                                               newEntry = new PeopleEntity(entryName);

                                     entry.getChildren().add(newEntry); // 新结点增加到数据模型中

                                     tv.add(entry, newEntry);// newEntry结点增加到entry之下,或用tv.refresh(entry,true)也行

                                     if (!tv.getExpandedState(entry)) // 如果entry是未展开结点则展开它

                                               tv.expandToLevel(entry, 1);

                            }

                   }

         }

         // 删除结点的Action类

         private class RemoveEntryAction extends Action {

                   public RemoveEntryAction() {

                            setText("删除");

                   }

                   public void run() {

                            ITreeEntry entry = getSelTreeEntry();

                            if (entry == null)

                                     return;

                            // 从数据模型里删除结点

                            List<ITreeEntry> list = (List<ITreeEntry>) tv.getInput();

                            remove(list, entry);

                            // 从界面删除结点,放在从模型删除之后,

                            //否则在删除某个结点的最后一个子结点时会出问题

                            tv.remove(entry);

                   }

                   private void remove(List<ITreeEntry> list, ITreeEntry entry) {

                            if (list == null)    return;

                            for (Iterator it = list.iterator(); it.hasNext();) {

                                     ITreeEntry o = (ITreeEntry) it.next();

                                     if (o.getName().equals(entry.getName())) {

                                               it.remove();

                                               return;

                                     } else {

                                               remove(o.getChildren(), entry);

                                     }

                            }

                   }

         }

         // 修改结点名称的Action类

         private class ModifyEntryAction extends Action {

                   public ModifyEntryAction() {

                            setText("修改");

                   }

                   public void run() {

                            ITreeEntry entry = getSelTreeEntry();

                            if (entry == null)         return;

                            InputDialog dialog = new InputDialog(null, "修改结点", "输入新名称", entry.getName(), null);

                            if (dialog.open() == InputDialog.OK) {

                                     String entryName = dialog.getValue();

                                     entry.setName(entryName);//修改数据模型

                                     tv.refresh(entry); // 刷新结点,等效于tv.update(entry,null);

                            }

                   }

         }

         // 为共用而自定义的方法:取得当前选择的结点

         private ITreeEntry getSelTreeEntry() {

                   IStructuredSelection selection = (IStructuredSelection) tv.getSelection();

                   return (ITreeEntry) (selection.getFirstElement());

         }

}

<!-- page -->
分享到:
评论

相关推荐

    DhtmlxTree-dhtmlxmenu实现在节点上右键弹出菜单

    为dhtmlXTree树上的每一个节点添加右键菜单。附:在树上的节点上点右键时才会生成菜单,空白区域单击时不会生成菜单。 分析: 1、用 dhtmlXTree + dhtmlxmenu 实现。 2、 用dhtmlxmenu生成菜单的部分代码: ...

    超级列表框添加右键菜单(全选、复制、取消)-易语言

    在易语言编程中,添加右键菜单到控件如超级列表框是常见的需求,这能够增强用户交互体验。...通过学习和实践,你将掌握如何在易语言中利用系统API创建自定义的右键菜单,提高程序的功能性和用户体验。

    系统右键扩展功能小工具

    为了解决这一问题,出现了名为“系统右键扩展功能”的小工具,它通过在系统右键菜单中增加快捷选项,使用户能够快速方便地切换显示或隐藏系统文件及扩展名,极大地提高了工作效率。 这款小工具的核心功能在于其提供...

    本算例实现一个任务栏托盘菜单,当用户右击该该图标时,就会弹出一个快捷菜单

    本算例实现了一个这样的功能,当用户右键点击任务栏托盘区的图标时,会弹出一个包含各种功能的快捷菜单。 实现任务栏托盘菜单主要涉及到以下几个关键知识点: 1. **Windows API**:Windows应用程序通常使用Windows...

    16在系统菜单里加上自己的菜单项.rar_在系统菜单

    在Windows操作系统中,自定义系统菜单意味着用户可以将自己的应用程序或者功能添加到开始菜单、右键菜单等系统级菜单中,方便快速访问。这个过程涉及到Windows的注册表编辑、上下文菜单扩展以及可能的快捷方式创建。...

    Windows电脑右键添加管理员身份运行

    本教程将详细介绍如何通过一个.bat批处理文件来实现为鼠标右键菜单添加“管理员身份运行”选项。 首先,我们需要理解Windows的用户账户控制(User Account Control, UAC)机制。UAC是为了提高系统安全性而设计的,...

    jQuery LigerUI V1.1.0

    [增加]ligerTab增加右键菜单功能,包括 关闭其他/关闭全部等。 [增加]ligerTab增加获取Items Count,删除项等常见方法 [增加]ligerLayout增加初始化控制左边/右边隐藏、是否折叠、是否调整大小等方法。 ...

    VB编程源代码 16在系统菜单里加上自己的菜单项.rar

    标题“VB编程源代码 16在系统菜单里加上自己的菜单项.rar”表明这是一个关于如何在VB程序中实现这一功能的源代码示例。描述中的内容再次确认了这一点,指出这是一个关于在系统菜单中添加自定义菜单项的VB源代码。 ...

    易语言高表格右键选中行并弹出菜单源码.docx

    总结来说,这段易语言代码实现了高表格组件的右键选择行并弹出菜单的功能,通过捕获和处理窗口消息,可以精确地识别用户的鼠标操作,并根据这些操作提供相应的上下文菜单功能。这在数据密集型的桌面应用中非常实用,...

    VS2010MFC编程入门之三十四(菜单:VS2010菜单资源详解)

    要在程序中实现快捷键功能,需在Accelerator资源中进行设置。Accelerator资源包括四列:ID、Modifier、Key和Type。ID对应菜单项的ID,Modifier和Key定义了组合键,如“Open”的ID为`ID_FILE_OPEN`,Modifier为“Ctrl...

    EditPLus添加到右键.docx

    总的来说,EditPlus的右键菜单集成让开发者在处理代码时能够更加高效,而上述两种方法提供了实现这一功能的不同途径。无论你是编程新手还是经验丰富的开发者,EditPlus都是一款值得尝试的文本编辑器。

    hypersnap

    从压缩包中的文件名“给JFace TreeViewer树加上右键菜单,及实现菜单相应功能_三的世界_百度空间.htm”来看,这应该是一篇详细的教程,讲解了如何为JFace TreeViewer添加上下文(右键)菜单,并实现菜单项的点击事件...

    PLSQL Developer之你不知道的几个比较炫的功能

    PLSQL Developer 还提供了其他一些实用的功能,例如可以快速清空表,使用 TRUNCATE TABLE 语句,并且可以在右键菜单中找到。 此外,PLSQL Developer 还提供了 Analyze 和 VALID 两个功能,但是这些功能的作用和使用...

    轻轻松松将你的程序加上TrayIcon

    6. **跨平台兼容性**:虽然以上讨论的是Windows环境下的TrayIcon,但其他操作系统如Linux和macOS也有相应的实现。例如,Linux可以使用libappindicator或dbusmenu,macOS则有StatusItem类。 7. **资源管理**:在程序...

    大学计算机office中文字处、电子表格、演示文稿的练习题.docx

    - 隐藏工具栏:显示隐藏的“常用”工具栏,可从“视图”菜单的“工具栏”选项或通过右键菜单实现。 - 自定义工具栏:可以通过“工具”菜单的“自定义”进行添加或删除工具栏。 - 文档操作:可通过“文件”菜单...

    MFC Menu框架设计

    开发者可以通过在菜单项的文本前加上"&"字符来指定快捷键。 9. **上下文敏感帮助**:MFC菜单框架也支持上下文敏感帮助,通过`ON_HELPINFO`消息映射宏,可以在用户按下F1时提供与当前选择菜单项相关的帮助信息。 ...

    vb程序设计各章习题答案

    最后,程序设计题涉及创建一个菜单,包含主菜单项和子菜单项,并在选择不同的进制转换时,相应菜单项前加上“复选”标记。这个练习旨在让学生理解菜单项的状态控制和事件处理,以及如何在代码中实现这些功能。 总结...

    FullCalendar扩展双击事件

    本文将深入探讨如何在FullCalendar中实现双击事件功能,包括源码修改和扩展方法,以兼容不同版本。 ### 1. 源码版双击事件 在源码版FullCalendar中添加双击事件功能,你需要直接修改FullCalendar的核心代码。首先...

    CATIA基础教程基本操作PPT学习教案.pptx

    命令输入行用于输入命令来执行相应的操作,所有输入的命令前必须都要加上“c:”才可以执行。 工作窗口介绍 工作窗口是用户的工作区域,主要包含以下几项基本内容: * 基准平面是一切工作的基准,xy平面、yz平面...

Global site tag (gtag.js) - Google Analytics