这两天花了不少时间在如何把从数据库中读到的内容显示在一个Editor中,因此总结下吧。
需求:数据库中保存了服务对应的wsdl文档,现在需要根据服务ID从数据库中读取该文档内容,然后显示在一个编辑器中,要求对xml文档能着色。
应该说想明白后很简单,只需要两三步就可以了。
1.编写一个类实现IStorage接口,我程序中取名为WsdlStorage,具体如下
import java.io.ByteArrayInputStream; import java.io.InputStream; import org.eclipse.core.resources.IStorage; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.PlatformObject; /** * 包装wsdl文档,使之能在编辑器中打开* * */ public class WsdlStorage extends PlatformObject implements IStorage { private InputStream inputStream;//wsdl文档对应的输入流 private String wsdlName;//wsdl对应的名字 public WsdlStorage(InputStream inputStream, String wsdlName) { super(); this.inputStream = inputStream; this.wsdlName = wsdlName; } /** * 返回要显示 的具体内容 */ @Override public InputStream getContents() throws CoreException { // TODO Auto-generated method stub return inputStream; } @Override public IPath getFullPath() { // TODO Auto-generated method stub return null; } /** * 返回在编辑器中显示的名字 */ @Override public String getName() { // TODO Auto-generated method stub return wsdlName; } /** * 设置成只读 */ @Override public boolean isReadOnly() { // TODO Auto-generated method stub return true; } }
2. 编写一个类实现IStorageEditorInput接口,我程序中是WsdlEditorInput,具体内容如下:
import java.io.InputStream; import org.eclipse.core.resources.IStorage; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.PlatformObject; import org.eclipse.jface.resource.ImageDescriptor; import org.eclipse.ui.IPersistableElement; import org.eclipse.ui.IStorageEditorInput; public class WsdlEditorInput extends PlatformObject implements IStorageEditorInput { private IStorage storage; public WsdlEditorInput(IStorage storage) { super(); this.storage=storage; } /** * 重点是这个方法 */ @Override public IStorage getStorage() throws CoreException { // TODO Auto-generated method stub return storage; } @Override public boolean exists() { // TODO Auto-generated method stub return false; } @Override public ImageDescriptor getImageDescriptor() { // TODO Auto-generated method stub return null; } @Override public String getName() { // TODO Auto-generated method stub return storage.getName(); } @Override public IPersistableElement getPersistable() { // TODO Auto-generated method stub return null; } @Override public String getToolTipText() { // TODO Auto-generated method stub return "toolTip:"+storage.getName(); } }
如果你只是用一般的文本编辑器打开,可以直接跳到第4步。
要用xml编辑器打开具体内容,还要实现着色功能,这里要做的事会稍微多些
3.我这里准备从eclipse plugin中自带的XMLEditor进行一些修改,使之符合我的要求。
把例子中的代码都拷到自己工程下,只要修改一个类即可为我所用。
XMLDocumentProvider修改如下 :
//继承自StorageDocumentProvider public class XMLDocumentProvider extends StorageDocumentProvider { //这个方法一定要改,其实只需加入输入参数Object element,其它不用动 protected void setupDocument(Object element,IDocument document) { if (document != null) { IDocumentPartitioner partitioner = new FastPartitioner( new XMLPartitionScanner(), new String[] { XMLPartitionScanner.XML_TAG, XMLPartitionScanner.XML_COMMENT }); partitioner.connect(document); document.setDocumentPartitioner(partitioner); } } protected IAnnotationModel createAnnotationModel(Object element) throws CoreException { return null; } }
4.写个上下文菜单,获得wsdl内容,然后在编辑器中打开 吧
/** * 用户选择一个服务时,打开该服务对应的wsdl文档 */ public class ShowWsdlCommandHandler extends AbstractHandler { int sid = -1; String serviceName = ""; @Override public Object execute(ExecutionEvent event) throws ExecutionException { IWorkbenchWindow window = HandlerUtil.getActiveWorkbenchWindow(event); IWorkbenchPage page = window.getActivePage(); // 获得当前选择的服务id和名字 ISelection selection = HandlerUtil.getActiveWorkbenchWindow(event) .getActivePage().getSelection(); if (selection != null && selection instanceof IStructuredSelection) { IStructuredSelection selections = (IStructuredSelection) selection; Object obj = selections.getFirstElement(); if (obj instanceof ServiceModel) { sid = ((ServiceModel) obj).getSid(); serviceName = ((ServiceModel) obj).getServiceName(); } } // 获得需要打开的wsdl内容 InputStream in = null; in = ServiceDAO.getWsdlContent(sid);//从数据库中读取wsdl文档 //在Editor中打开 IStorage storage = new WsdlStorage(in, serviceName); IStorageEditorInput input = new WsdlEditorInput(storage); if (page != null) try { //用xml编辑器打开 page.openEditor(input,XMLEditor.ID); //如果只想用普通编辑器打开,则直接调用下面代码 更简单 //page.openEditor(input,EditorsUI.DEFAULT_TEXT_EDITOR_ID); } catch (PartInitException e) { e.printStackTrace(); } return null; } }
大家关心的应该没几行,从第24行开始看就行了,只要你的程序能获得一个InputStream,替换掉我的代码应该就可以用了。
前面说过,如果你只想用一般的编辑器打开一些内容,那么省略到第三步,第四步中直接 调用
page.openEditor(input,EditorsUI.DEFAULT_TEXT_EDITOR_ID);
即可,应该很简单的。
如果大家觉得第三步看不懂,不妨先想想如何实现打开一个外部的xml文件。。。这个会了,打开非文件的内容也就会了。
附1:如果运行中会出现问题,不妨试试在plugin.xml中的dependencies中加上下面三个:
org.eclipse.ui.workbench.texteditor;
org.eclipse.jface.text;
org.eclipse.ui.editors;