跳转到主要内容

单击提交则表示您同意developerWorks 的条款和条件。 查看条款和条件.

当您初次登录到 developerWorks 时,将会为您创建一份概要信息。您在 developerWorks 概要信息中选择公开的信息将公开显示给其他人,但您可以随时修改这些信息的显示状态。您的姓名(除非选择隐藏)和昵称将和您在 developerWorks 发布的内容一同显示。

所有提交的信息确保安全。

  • 关闭 [x]

当您初次登录到 developerWorks 时,将会为您创建一份概要信息,您需要指定一个昵称。您的昵称将和您在 developerWorks 发布的内容显示在一起。

昵称长度在 3 至 31 个字符之间。 您的昵称在 developerWorks 社区中必须是唯一的,并且出于隐私保护的原因,不能是您的电子邮件地址。

单击提交则表示您同意developerWorks 的条款和条件。 查看条款和条件.

所有提交的信息确保安全。

  • 关闭 [x]

基于 JFace Text Framework 构建全功能代码编辑器: 第 8 部分:Hyperlink

马 若劼 (maruojie@cn.ibm.com), 软件工程师, IBM 中国软件开发中心
马若劼是 Lotus Forms 部门的一位软件工程师,主要从事电子表单技术的研发工作。他在 Eclipse 和 Java 方面有多年研发经验,同时也是国内著名开源项目 LumaQQ 的创立者

简介: Hyperlink(超链接)一般用来在编辑器中实现快速的代码定位,当然它并不局限与此,你可以自定义超链接的行为。本文介绍超链接的概念和在 JTF 中的实现方式。

查看本系列更多内容

发布日期: 2008 年 4 月 24 日
级别: 中级
访问情况 : 1407 次浏览
评论: 


Hyperlink

Hyperlink(超链接)在 Java 编辑器中用来进行快速的代码定位,当你按住 Ctrl 键并把鼠标指向一个函数名的时候,函数名会显示为超链接,点击之后代码会跳转到函数的声明处。这个功能使得 Eclipse 浏览代码很方便,这次我就来介绍如何在自己的编辑器中添加超链接功能。

超链接的定位

编辑器不会知道哪块区域应该显示为超链接,这是通过 IHyperlinkDetector 接口实现的。这里牵涉到语义方面的内容,因为你必须要能知道鼠标下面到底是个什么。在解析器那一层需要实现这样的支持。

超链接的渲染

JTF 是如何显示超链接的?可能你会想到标注,缺省的实现不是这样。这里要介绍另外一个接口:IHyperlinkPresenter。JTF 缺省的时候是用 StyledText 的 StyleRange 实现的,其实就是把超链接的那块文字置为蓝色且带下划线。但是因为有了这么一个接口,你可以把超链接弄成任何样子。


实现超链接

本文要实现的超链接功能是:点击某个变量名,编辑器会选中声明该变量的那条语句。

底层支持

底层需要支持两个功能:判断某个位置是一个变量,以及得到变量声明的语句范围。由于我的例子很简单,判断是不是变量也非常简单,只要符号类型是一个 ID 类型就行了。得到变量声明的语句范围需要检查语法树,因为变量声明的子树以等号为根节点,所以找到对应的根节点就行了。然后从等号开始得到子树的最左和最右节点,从而计算出整个子树的字符范围。这些代码已经添加到了 TreeHelper 中,具体请参看 getVariableDeclaration 和 getTreeRange 方法。

实现 IHyperlink

我实现了一个 VariableHyperlink 来封装超链接信息,它最重要的方法是 open(),因为它会在你点击超链接后被调用:


清单1. VariableHyperlink 的 open 方法
                
   
public void open() {
	// get doc
	IDocument doc = viewer.getDocument();
	
	// get tree
	Tree tree = TreeManager.getTree(doc);
	
	// get variable declaration range
	Point range = TreeHelper.getVariableDeclaration(tree, variable);
	
	// select text
	if(range != null) {
		viewer.setSelectedRange(range.x, range.y);
		viewer.revealRange(range.x, range.y);
	}
}

我用到了刚才提到的 TreeHelper 中的方法来得到声明语句的范围,剩下的事情就比较直接了,选择这个范围并让确保其在编辑器中可见。

实现 IHyperlinkDetector

ExprHyperlinkDetector 完成了发现变量的功能,然后把变量信息包装在 VariableHyperlink 中。在之前的文章中,我已经不止一次的使用了 TokenList 来得到某个偏移处的符号,ExprHyperlinkDetector 也依赖于 TokenList,所以这里不详细解释了。

配置

覆盖 ExprConfiguration 的 getHyperlinkDetectors,让它返回 ExprHyperlinkDetector。它的返回值是一个数组,所以你可以安装多个 IHyperlinkDetector 实例。对于这个简单的小例子,并无必要使用多个 IHyperlinkDetector 实例。


结束语

超链接是 JTF 中相对简单的一个功能了,但是不要忘了,我是没有实现全部的功能的:

  1. 是不是一定需要按住 Ctrl 键才能激活超链接功能呢?不是,请看看 SourceViewerConfiguration 的 getHyperlinkStateMask 方法。
  2. 试试看使用 IHyperlinkPresenter 实现一个自定义的超链接样式,这里牵涉到 HyperlinkManager 这个类的使用。这个功能较为复杂一些,需要这样做的时候也不多,没有时间的读者不妨看看 DefaultHyperlinkPresenter 类的实现。
  3. 例子还是有 bug 的,比如如果一个变量声明了两次,则只会选择第一条声明语句。可以考虑显示一个浮动窗口来选择跳转到哪个,你想到了什么解决方案呢?

声明

本文仅代表作者的个人观点,不代表IBM的立场。



下载

描述名字大小下载方法
第八小节示例代码jtf.tutorial.part8.zip1140KBHTTP

关于下载方法的信息


参考资料

关于作者

马若劼是 Lotus Forms 部门的一位软件工程师,主要从事电子表单技术的研发工作。他在 Eclipse 和 Java 方面有多年研发经验,同时也是国内著名开源项目 LumaQQ 的创立者

关于报告滥用的帮助

报告滥用

谢谢! 此内容已经标识给管理员注意。


关于报告滥用的帮助

报告滥用

报告滥用提交失败。 请稍后重试。


developerWorks:登录


需要一个 IBM ID?
忘记 IBM ID?


忘记密码?
更改您的密码

单击提交则表示您同意developerWorks 的条款和条件。 使用条款

 


当您初次登录到 developerWorks 时,将会为您创建一份概要信息。您在 developerWorks 概要信息中选择公开的信息将公开显示给其他人,但您可以随时修改这些信息的显示状态。您的姓名(除非选择隐藏)和昵称将和您在 developerWorks 发布的内容一同显示。

请选择您的昵称:

当您初次登录到 developerWorks 时,将会为您创建一份概要信息,您需要指定一个昵称。您的昵称将和您在 developerWorks 发布的内容显示在一起。

昵称长度在 3 至 31 个字符之间。 您的昵称在 developerWorks 社区中必须是唯一的,并且出于隐私保护的原因,不能是您的电子邮件地址。

(长度在 3 至 31 个字符之间)


单击提交则表示您同意developerWorks 的条款和条件。 使用条款.

 


为本文评分

评论

static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=10
Zone=Open source
ArticleID=302558
ArticleTitle=基于 JFace Text Framework 构建全功能代码编辑器: 第 8 部分:Hyperlink
publish-date=04242008
author1-email=maruojie@cn.ibm.com
author1-email-cc=

标签

Help
使用 搜索 文本框在 My developerWorks 中查找包含该标签的所有内容。

使用 滑动条 调节标签的数量。

热门标签 显示了特定专区最受欢迎的标签(例如 Java technology,Linux,WebSphere)。

我的标签 显示了特定专区您标记的标签(例如 Java technology,Linux,WebSphere)。

使用搜索文本框在 My developerWorks 中查找包含该标签的所有内容。热门标签 显示了特定专区最受欢迎的标签(例如 Java technology,Linux,WebSphere)。我的标签 显示了特定专区您标记的标签(例如 Java technology,Linux,WebSphere)。