要了解swt,jface的一些机制,不过大部分都可以查阅资料清楚具体的用法。
这次代码生成插件的开发首先遇到的难点是模块的构建次序,按照jsmart的工作流程,数据库加载,实体构建,包名设定,框架选择。各模块之间的关联处理比较麻烦,主要是一些参数的传递。第一步将框架搭建起来。
第二个难点是plugin.xml的配置,其中runtime的配置没写,也就是插件运行环境的jar包没有加载,是的插件运行时总是报错,这个错误调了很久,破费周折。发现这一类的问题插件本身不会报错,但是会转向event事件的处理,感觉这种错误太隐蔽了。
第三个难点是rcp的路径选择问题。很麻烦,从这个才知道了Eclipse中有一个jdt包,包含了Eclipse工程的很多信息,感觉相当实用。路径的一些现实代码如下:
代码 package testplugin.actions; import java.net.URL; import org.eclipse.ui.IWorkbenchWindow; import org.eclipse.ui.IWorkbenchWindowActionDelegate; import org.eclipse.ui.internal.UIPlugin; import org.eclipse.core.resources.IProject; import org.eclipse.core.runtime.Platform; import org.eclipse.core.runtime.adaptor.LocationManager; import org.eclipse.jdt.core.IJavaProject; import org.eclipse.jface.viewers.ISelection; import org.eclipse.jface.viewers.IStructuredSelection; import org.eclipse.jface.action.IAction; import org.eclipse.jface.dialogs.MessageDialog; import org.eclipse.osgi.service.datalocation.Location; import org.osgi.framework.Bundle; import testplugin.Activator; /** * Our sample action implements workbench action delegate. The action proxy will * be created by the workbench and shown in the UI. When the user tries to use * the action, this delegate will be created and execution will be delegated to * it. * * @see IWorkbenchWindowActionDelegate */ public class SampleAction implements IWorkbenchWindowActionDelegate { private IWorkbenchWindow window; private static IProject project = null; /** * The constructor. */ public SampleAction() { } /** * The action has been activated. The argument of the method represents the * 'real' action sitting in the workbench UI. * * @see IWorkbenchWindowActionDelegate#run */ public void run(IAction action) { Location installLoc = LocationManager.getInstallLocation(); String path = null; String installPath = null; if (installLoc != null) { URL installURL = installLoc.getURL(); // assume install URL is file: based path = installURL.getPath(); } installPath = path.substring(1, path.length()); Bundle bundle = Platform.getBundle("webGenerator"); String bundleLocation = bundle.getLocation(); String resource = SampleAction.class.getResource("generator.properties").toString(); String msg; msg = "plugin abstract path:" + Activator.getDefault().getStateLocation().makeAbsolute().toFile().getAbsolutePath(); msg += "\nworkspace:" + Platform.getInstanceLocation().getURL().getPath(); msg += "\ninstallPath:" + installPath; msg += "\n" + UIPlugin.getDefault().getBundle().getHeaders().get("Bundle-Name"); msg += "\n" + bundleLocation; msg += "\n" + resource; MessageDialog.openInformation(window.getShell(), "TestPlugin", msg); } /** * Selection in the workbench has been changed. We can change the state of * the 'real' action here if we want, but this can only happen after the * delegate has been created. * * @see IWorkbenchWindowActionDelegate#selectionChanged */ public void selectionChanged(IAction action, ISelection selection) { // Test project resource selection if (selection instanceof IStructuredSelection) { String msg; IStructuredSelection structuredSelect = (IStructuredSelection) selection; if (!structuredSelect.isEmpty()) { Object obj = structuredSelect.getFirstElement(); if (obj instanceof IProject) { project = ((IProject) obj).getProject(); msg = "getProjectName:" + getProjectName(); msg += "getWorkplaceName:" + getWorkplaceName(); msg += "getProjectPath:" + getProjectPath(); msg += "getPath:" + getPath(); msg += "getPluginPath:" + getPluginPath(); MessageDialog.openInformation(window.getShell(), "TestPlugin", msg); return; } else { System.out.println("The selection is not a project"); } } } } /** * We can use this method to dispose of any system resources we previously * allocated. * * @see IWorkbenchWindowActionDelegate#dispose */ public void dispose() { } /** * We will cache window object in order to be able to provide parent shell * for the message dialog. * * @see IWorkbenchWindowActionDelegate#init */ public void init(IWorkbenchWindow window) { this.window = window; } /** * 得到项目名称 * * @return */ public static String getProjectName() { return project.getName(); } /** * 得到workplace的运行文件 * * @return */ public static String getWorkplaceName() { String path = Platform.getInstanceLocation().getURL().getPath(); return path.substring(1, path.length()); } /** * 得到project项目的文件路径 * * @return */ public static String getProjectPath() { return project.getProject().getLocation().toString() + "/"; } /** * 得到Eclipse运行目录 * * @return */ @SuppressWarnings("restriction") public static String getPath() { Location installLoc = LocationManager.getInstallLocation(); String path = null; String installPath = null; if (installLoc != null) { URL installURL = installLoc.getURL(); // assume install URL is file: based path = installURL.getPath(); } installPath = path.substring(1, path.length()); return installPath; } /** * 得到plugin所在的位置,文件夹为.../filename/;jar包为.../filename.jar * * @return */ public static String getPluginPath() { Bundle bundle = Platform.getBundle("webGenerator"); String bundleLocation = bundle.getLocation(); String[] items = bundleLocation.split(":"); String pluginLocation = getPath() + items[items.length - 1]; return pluginLocation; } }
这次项目对插件的认识姑且就是这些,虽然相当肤浅,不过也算是了解的,感觉Eclipse的却比较强大,java也很强大。感觉像在编程上有所成就真是任重而道远啊。
什么时候要吧Eclipse的框架理一下啊!