`

【Eclipse插件开发】打开编辑器(转)

 
阅读更多

今天终于可以闲一天,想来想去就乱写点东西吧,说不定对有些新人有点帮助呢~_~
        用Eclipse API的方式来打开编辑器,可能对任何一个插件开发者都不是很陌生的操作了。但是,还是建议你忍着看一下,全当是复习吧~_~。
       
        【打开editor的接口讨论】
        先来看一下workbench吧,workbench从静态划分应该大致如下:
       
            从结构图我们大致就可以猜测出来,workbench page作为一个IWorkbenchPart(无论是eidtor part还是view part)的容器,肯定会接受workbench page的管理。看了一下,IWorkbenchPage接口定义中确实提供给了如下打开编辑器的操作:

             【IWokbenchPage提供的接口】

1 public interface IWorkbenchPage extends IPartService, ISelectionService,ICompatibleWorkbenchPage {
2     
3      public IEditorPart openEdito(IEditorInput input, String editorId)throws PartInitException;
4      
5      public IEditorPart openEdito(IEditorInput input, String editorId, boolean activate) throws PartInitException;
6    
7      public IEditorPart openEditor(final IEditorInput input, final String editorId, final boolean activate, final int matchFlags)throws PartInitException;
8 }
          
            那到这边,可能很多人已经知道了怎么调用这些接口了:
           PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage().openEditor(...)
          (说明:PlatformUI可以看作是整个eclipse ui框架的门面类,当然最核心的作用就是让用户获取到workbench。Eclipse中存在的其他一些门面类如:ResourcesPlugin、Platform、JavaCore、JavaUI等)

            我们再仔细看一下IWorkbenchPage对应的实现类(org.eclipse.ui.internal.WorkbenchPage)中的以上接口的实现代码,真正在管理Editor的是一个叫做EditorManager的东东(同理,view part对应的管理器角色类是叫做ViewFactory的东东)。这里的EditorManager和View Factory是workbench实现中非常精华的部分,看一下里面的实现就会很大程度上理解workbench所谓懒加载、懒初始化是如何实现的了,如何实现part 复用的...等等。 
            
           上图就用来说明workbench是如何来管理各种part的,其中descriptor角色的核心作用是延迟加载扩展(延迟加载用户通过editors或者views提供的扩展),reference角色的核心作用是用来延迟初时化具体的part(例如避免过早的创建对应的control等等)。再说下去有点偏离主题了,这部分,以后有时间再写
            
           【IDE工具类提供的接口】
            上面IWorkbenchPage提供接口都需要用户准备两样东西:一是创建IEditorInput实例,二是指定editor id。有些用户可能不想干这两件事情,所以在工具类org.eclipse.ui.ide.IDE中提供了其他的接口:
            
 1 public static IEditorPart openEditor(IWorkbenchPage page, IFile input) throws PartInitException { }
 2 
 3 public static IEditorPart openEditor(IWorkbenchPage page, IFile input, boolean activate) throws PartInitException {  }
 4 
 5 public static IEditorPart openEditor(IWorkbenchPage page, IFile input, boolean activate, boolean determineContentType) { }
 6 
 7 public static IEditorPart openEditor(IWorkbenchPage page, IFile input, String editorId) throws PartInitException {  }
 8 
 9 public static IEditorPart openEditor(IWorkbenchPage page, IFile input, String editorId, boolean activate) throws PartInitException {  }
10 
11 
           上面5个接口操作中, 对于上面的三个操作,Eclipse会自动为你准备IEditorInput实例,并动态绑定合适的编辑器类型。对于下面的两个操作,Eclipse会为你自动准备IEditorInput实例,但是需要用户自己指定editor id。
            
           接下来我们看两个问题,一是如何创建IEditorInput实例的;而是如何动态计算对应的editor id的。
           
          【有关FileEditorInput】
           在IDE工具类中提供的5个接受IFile对象的openEditor接口中,在对应的实现中都是默认构造了一个FileEditorInput(org.eclipse.ui.part.FileEditorInput)实例,这个实例也是org.eclipse.ui.IFileEditorInput接口的默认实现类(注意:Eclipse中很多地方都使用这种Interface/Default Impl的方式,Interface会暴露,Default Impl则根据情况选择是否暴露,一般是如果Interface希望用户来扩展继承,则会暴露对应的Default Impl,如果Interface不希望用户来扩展继承,例如IResource系列接口,则一般会将Default Impl丢如对应的internal包中)。
            我们看一下org.eclipse.ui.part.FileEditorInput中是如何实现IEditorInput.exists()接口的:
1 public class FileEditorInput implements IFileEditorInput,IPathEditorInput,IPersistableElement {
2     private IFile file;
3 
4     public boolean exists() {
5         return file.exists();
6     }
7 }
          我们看到内部的实现是持有了IFile句柄,如果IFile代表的资源没有存在于工作区之内,那么就会返回false。(疑问:如果我们打开工作区外部的文件呢???显然,FileEditorInput并不合适,稍后看...)
        
        【动态计算editor id】
         下面,我们再来看一下IDE类是如何计算所谓的默认eidtor id的。追踪实现,我们看到了IDE.getDefaultEditor
          
 1  public static IEditorDescriptor getDefaultEditor(IFile file, boolean determineContentType) {
 2         // Try file specific editor.
 3         IEditorRegistry editorReg = PlatformUI.getWorkbench()
 4                 .getEditorRegistry();
 5         try {
 6             String editorID = file.getPersistentProperty(EDITOR_KEY);
 7             if (editorID != null) {
 8                 IEditorDescriptor desc = editorReg.findEditor(editorID);
 9                 if (desc != null) {
10                     return desc;
11                 }
12             }
13         } catch (CoreException e) {
14             // do nothing
15         }
16         
17         IContentType contentType = null;
18         if (determineContentType) {
19             contentType = getContentType(file);
20         }    
21         // Try lookup with filename
22         return editorReg.getDefaultEditor(file.getName(), contentType);
23     }
            上面的代码大致赶了如下两件事情:
            1、如果对应的资源设定了一个特定的持久化属性EDITOR_KEY,则会使用EDITOR_KEY属性值所代表的编辑器(说明:有关Eclipse资源的属性支持,请参阅其他文档)。那如果一个资源不在工作区之内,又如何设定EDITOR_KEY属性呢???  (~_~确实没法设定)
           2、查找对应的content type,用户通过org.eclipse.core.runtime.contentTypes扩展点来注册自定义的内容类型,在内容类型中会指定对应的文件扩展名和默认编码,例如JDT中注册了如下内容类型(摘自org.eclipse.jdt.core/plugin.xml):
<!-- =================================================================================== -->
<!-- Extension: Java Content Types                                                       -->
<!-- =================================================================================== -->
<extension point="org.eclipse.core.runtime.contentTypes">
    <!-- declares a content type for Java Properties files -->
    <content-type id="javaProperties" name="%javaPropertiesName" 
        base-type
="org.eclipse.core.runtime.text"
        priority
="high"                
        file-extensions
="properties"
        default-charset
="ISO-8859-1"/>
    <!-- Associates .classpath to the XML content type -->
    <file-association 
        
content-type="org.eclipse.core.runtime.xml" 
        file-names
=".classpath"/>  
    <!-- declares a content type for Java Source files -->
    <content-type id="javaSource" name="%javaSourceName" 
        base-type
="org.eclipse.core.runtime.text"
        priority
="high"                
        file-extensions
="java"/>
    <!-- declares a content type for Java class files -->
    <content-type id="javaClass" name="%javaClassName" 
        priority
="high"                
        file-extensions
="class">        
        <describer
            
class="org.eclipse.core.runtime.content.BinarySignatureDescriber">
            <parameter name="signature" value="CA, FE, BA, BE"/>
        </describer>
    </content-type>        
    <!-- declares a content type for JAR manifest files -->
    <content-type id="JARManifest" name="%jarManifestName" 
        base-type
="org.eclipse.core.runtime.text"
        priority
="high"                
        file-names
="MANIFEST.MF"
        default-charset
="UTF-8"/>
</extension>
             那如果我们在注册编辑器的时候和对应的content type绑定,这不就联系起来了吗~_~。那我们看一下java源码编辑器扩展描述(摘自org.eclipse.jdt.ui/plugin.xml):
<editor
            
name="%JavaEditor.label"
            default
="true"
            icon
="$nl$/icons/full/obj16/jcu_obj.gif"
            contributorClass
="org.eclipse.jdt.internal.ui.javaeditor.CompilationUnitEditorActionContributor"
            class
="org.eclipse.jdt.internal.ui.javaeditor.CompilationUnitEditor"
            symbolicFontName
="org.eclipse.jdt.ui.editors.textfont"
            id
="org.eclipse.jdt.ui.CompilationUnitEditor">
            <contentTypeBinding
               
contentTypeId="org.eclipse.jdt.core.javaSource"
            
/> 
      </editor>

           我们看到上面的xml中有contentTypeBinding元素,里面指定了绑定java源码content type。

            那如果我们在注册编辑器的时候,没有绑定对应的content type呢?Eclipse允许你配置,往下看:

            
            

            我想看到这边对eclipse如何动态计算一个文件对应的editor应该是明白了吧,再回顾一下吧:
            1、查看资源本身是否有EIDTOR_ID持久属性(注意:一、只有工作区中存在的资源才允许设置持久属性;二、资源属性知识针对特定资源,不会影响同类型资源,即你对工作区中特定的.java文件设定了EIDTOR_ID持久属性,并不会影响工作区中其他.java文件资源的编辑器绑定操作)
            2、查找对应的content type,然后查找对应的editor扩展或者查找Eclipse中的Content Types和File Associations配置
            3、如果都找不到,则直接给一个默认的编辑器。例如,我们经常碰到是"org.eclipse.ui.DefaultTextEditor"

            【IDE工具类提供的接口 VS  IWorkbenchPage提供的接口】
              看一下以上提到的各个角色之间的调用关系图吧:
              

        【使用Eclipse提供的打开editor的接口】
        还是那句话,需求决定一切。我们看一下打开编辑器的需求:
        1、打开工作区中工程内的文件资源
        2、打开工作区.metadata目录中的文件资源
        3、打开工作区外部的文件资源

        【说明】Eclipse工作区实际上是有数据区和元数据区两个区域组成的,示意如下:
        
            
            对于Eclipse来说,.metadata目录下存放的是插件运行时的关键状态数据,不建议用户再工作区实例运行期间做相应修改,为此eclipse干了两件事情:1、运行期间会自动在.metadata目录下产生一个进程锁定的.lock文件;2、Eclipse不允许用户通过IResource系列接口直接访问或修改.meatadata目录下的资源

           【打开工作区工程内的资源】
            
 假设工作区中有测试工程TestProject,工程下有文本文件java_file.txt。对应创建代码如下:
            
 1 try {
 2             //创建工程
 3             IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject("TestProject");
 4             if (!project.exists())
 5                 project.create(null);
 6             if (!project.isOpen())
 7                 project.open(null);
 8             
 9             //创建文件
10             IFile java_file = project.getFile(new Path("/java_file.txt"));
11             InputStream inputStreamJava = new ByteArrayInputStream("class MyType{}".getBytes());
12             if (!java_file.exists())
13                 java_file.create(inputStreamJava, falsenull);
14         } catch (CoreException e) {
15             IStatus status = new Status(IStatus.ERROR, "myplugin", 101, "创建资源失败", e);
16             Activator.getDefault().getLog().log(status);
17         }

            
        
        打开方式一:Eclipse默认计算对应的editor id,会用default text editor打开 
 1 try {
 2             IWorkbenchPage page = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage();
 3             IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject("TestProject");
 4             
 5             IFile java_file = project.getFile(new Path("/java_file.txt"));
 6             IDE.openEditor(page, java_file);            
 7         } catch (CoreException e) {
 8             IStatus status = new Status(IStatus.ERROR, "myplugin", 102, "打开工作区内文件出错", e);
 9             Activator.getDefault().getLog().log(status);
10         }

        打开方式二:指定java源码编辑器打开,会用java源码编辑器打开
 1 try {
 2             IWorkbenchPage page = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage();
 3             IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject("TestProject");
 4             
 5             IFile java_file = project.getFile(new Path("/java_file.txt"));
 6             IDE.openEditor(page, java_file, "org.eclipse.jdt.ui.CompilationUnitEditor");
 7         } catch (CoreException e) {
 8             IStatus status = new Status(IStatus.ERROR, "myplugin", 102, "打开工作区内文件出错", e);
 9             Activator.getDefault().getLog().log(status);
10         }

         
           打开方式三:设定editor id属性,该文件以后默认都用此editor id打开
 1 try {
 2             IWorkbenchPage page = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage();
 3             IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject("TestProject");
 4             
 5             IFile java_file = project.getFile(new Path("/java_file.txt"));
 6             java_file.setPersistentProperty(IDE.EDITOR_KEY, "org.eclipse.jdt.ui.CompilationUnitEditor");
 7             IDE.openEditor(page, java_file);
 8         } catch (CoreException e) {
 9             IStatus status = new Status(IStatus.ERROR, "myplugin", 102, "打开工作区内文件出错", e);
10             Activator.getDefault().getLog().log(status);
11         }

        说明:对于工作区工程内的资源,可以有两种方式:一是local的,那就是物理存在与工程之内;二是link进入的。打开编辑器的时候,不需要做区分。

        【打开工作区外部的资源】
        说明:既存在于工作区外部,同时又没有被link进工程。
        
        在Eclipse中有个功能,就是File->Open File,可以打开一个外部文件。那我们看一下它是怎么实现的。我们只需要打开对应的对话框,然后挂起主线程,就可以找到对应的action了(挂起线程可以帮我们很方便的调试很多类型的问题,以后细说~_~):
                      

           分析一下OpenExternalFileAction的实现,我们发现它自己构建了一个editor input
分享到:
评论

相关推荐

    eclipse插件开发-编辑器详解

    在深入探讨Eclipse插件开发中编辑器的具体实现之前,我们首先需要明确几个关键概念。Eclipse作为一款强大的集成开发环境(IDE),其内部架构高度模块化,支持丰富的插件扩展机制。在这个过程中,`IWorkbenchPart`...

    eclipse插件开发form编辑器

    ### Eclipse插件开发Form编辑器的关键知识点 #### 一、Eclipse Forms简介 Eclipse Forms是一种用于创建丰富客户端界面的技术,它可以让你的应用程序在不使用Web浏览器的情况下展现出类似Web的效果。这种技术允许...

    eclipse插件开发打开编辑器.pdf

    综上所述,Eclipse插件开发中打开当前项目编辑器的流程主要包括获取工作台窗口、页面、项目、文件路径和打开编辑器的步骤。同时,需要自定义辅助方法来获取当前编辑器关联的项目名称和文件路径,以确保正确地定位到...

    《Eclipse 插件开发》源代码

    在Eclipse插件开发中,首先要了解的是Oxygen(早期版本称为PDE,Plugin Development Environment),这是Eclipse用于创建、调试和管理插件的工具集。通过PDE,开发者可以使用XML描述符(plugin.xml)定义插件的元...

    eclipse插件开发学习笔记配套源码

    这份"eclipse插件开发学习笔记配套源码"提供了一手的实践材料,帮助我们理解并掌握Eclipse插件的开发流程和技术要点。 Eclipse插件开发基于OSGi框架,该框架允许模块化构建应用程序,使得组件之间可以独立升级和...

    eclipse RCP开发的编辑器

    开发Eclipse RCP编辑器的第一步是创建一个新的Eclipse插件项目。在Eclipse IDE中,可以通过"File" -&gt; "New" -&gt; "Plug-in Project"来实现。在此过程中,你需要为项目命名,选择模板,并配置项目的依赖。确保选中"Plug...

    Eclipse 打开文件插件

    Eclipse是一款广泛使用的开源集成开发环境(IDE),主要用于Java编程,但通过安装各种插件,也可以支持其他编程语言。"Eclipse 打开文件插件"是为提升Eclipse平台用户体验而设计的一个实用工具,它使得在Eclipse中...

    eclipse提示插件开发

    总的来说,Eclipse插件开发是一个涉及多方面知识的过程,包括理解OOP(面向对象编程)、Eclipse插件架构、PDE工具的使用,以及可能的第三方库集成。通过创建一个简单的“Hello, World!”编辑器,你可以逐步熟悉这个...

    Eclipse插件开发--gef开发指南与入门系列宝典

    本指南将深入探讨Eclipse插件开发中的GEF框架,帮助开发者快速入门并掌握相关知识。 首先,让我们理解Eclipse插件开发的基本概念。Eclipse采用插件化架构,每个功能模块都是一个独立的插件,这些插件通过OSGi(Open...

    eclipse二级制编辑器插件.zip

    在Eclipse中集成二进制编辑器插件后,开发者可以在打开项目或资源时选择这个编辑器来查看二进制文件。该插件可能提供了诸如十六进制视图、查找和替换功能、以及对特定二进制格式(如图片、音频、或固件)的支持。这...

    Eclipse 可视化编辑器插件安装

    2. **打开编辑器**: 在项目中打开一个文件,右键点击选择“Open With”,然后在弹出的菜单中选择刚刚安装的可视化编辑器。 3. **设计界面**: 使用可视化编辑器,你可以通过拖拽控件、调整布局来设计用户界面,而...

    eclipse插件开发常用技巧

    给定IMember对象(如方法),先获取对应的ICompilationUnit,然后打开编辑器并定位到该成员。 创建新包和Java源文件,可以通过IPackageFragmentRoot和IPackageFragment接口完成。例如,可以获取当前工程的...

    资源文件编辑器(eclipse插件)

    Eclipse插件机制是实现资源文件编辑器功能的关键。开发者可以利用Eclipse开放的API创建自定义的编辑器插件,以支持特定类型的文件或满足特定需求。这些插件可以扩展Eclipse的默认功能,例如添加新的编辑器视图、增加...

    eclipse插件的开发基本步骤

    通过深入学习和实践,你可以掌握更多高级特性,如自定义编辑器、透视图、工作流等,从而创建出功能强大且个性化的开发环境。"开发Eclipse插件的基本步骤.ppt"这份文件很可能是详细的PPT教程,建议结合文件内容进行...

    eclipse插件开发指南

    在“Eclipse插件开发.doc”和“eclipse插件开发指南.pdf”这两份文档中,你应该能找到关于如何创建插件项目、编写插件代码、配置plugin.xml、设计用户界面以及调试插件的详细步骤和示例。这些资源将帮助你逐步掌握...

    eclipse插件开发-JDT.pdf

    Eclipse 插件开发 - JDT Eclipse 插件开发中的 JDT(Java Development Tools)是用于定义 Java 核心元素和 API 的插件。在开发特定于 Java 的功能部件时,总是应该将此插件列示为先决条件。JDT 核心包使您能够访问 ...

    Eclipse插件开发扩展点API中文.chm

    "Eclipse插件开发扩展点API中文.chm"文档就是为帮助开发者理解并使用Eclipse插件开发中的扩展点API而编写的中文指南。 扩展点(Extension Point)是Eclipse插件框架的关键概念,它是插件之间进行交互和扩展的基础。...

    Eclipse插件之properties编辑器.rar

    这个rar压缩包“Eclipse插件之properties编辑器”显然提供了一个专门用于编辑这类文件的工具。 Properties编辑器插件为开发者提供了更高效、便捷的方式来管理和编辑.properties文件。以下是一些关键知识点: 1. **...

Global site tag (gtag.js) - Google Analytics