Classloader-Fehler bei Export von Eclipse-Plugin mit OpenGL

commic

Grünschnabel
Hallo,

den ganzen Tag habe ich nach einer Lösung für mein Problem gesucht und leider noch nichts gefunden. Folgende Problemstellung:
Ich habe mir das Beispiel von Eclipse genommen um einen drehenden Torus animiert durch OpenGL (jogl) in einem SWT-Display darzustellen. Dieses Beispiel funktioniert auch wunderbar. Wer es selber ausprobieren will, hier der Link:
http://www.java2s.com/Code/Java/SWT-JFace-Eclipse/drawarotatingtorususingtheJOGLOpenGLbinding.htm
Beim Ausführen dann noch beachten, dass man bei VM-Arguments den Ordner angeben muss, worin sich jogl.jar, gluegen-rt.jar und swt.jar mit den ganzen dll-/ so- Bibliotheken für Windows (oder Linux...) befinden. Also: -Djava.library.path = "laufwerk:\pfad..."
Nun aber mein Problem. Wenn ich das ganze in einen ViewPart für ein EclipsePlugin packe, bekommen ich einen Classloader-Fehler. Er kann also die OpenGL-Bibliotheken nicht finden. Ich habe mittlerweile schon sehr viel probiert. Mit lwjgl habe ich das gleiche Problem. Und ich habe bis jetzt auch nicht eine Grafikbibliothek als Eclipse-Plugin gefunden, welches ich somit als abhängiges plugin von meinem benennen könnte. Dann habe ich mich noch versucht aus den Bibliotheken mit Hilfe von Eclipse ein eignes Plugin zu basteln (new-> plugin from existing jar-files). Versuche ich das jedoch, läd Eclipse nicht mehr, sobald ich mein Plugin in einem neuen Eclipse-Fenster starten will. Mache ich etwas falsch? Habe ich irgendwas vergessen ?

help :confused:

Danke schonmal für zahlreiche posts
 
Ok. Hier der Code von meinem View:

Code:
package ect.views;

import javax.media.opengl.GL;
import javax.media.opengl.GLContext;
import javax.media.opengl.GLDrawableFactory;
import javax.media.opengl.glu.GLU;

import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.opengl.GLCanvas;
import org.eclipse.swt.opengl.GLData;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.ui.part.ViewPart;

public class DiagramView extends ViewPart {

	public DiagramView() {
		// TODO Auto-generated constructor stub
	}

	@Override
	public void createPartControl(Composite parent) {
		final Composite comp = new Composite(parent, SWT.NONE);
		comp.setLayout(new FillLayout());
		GLData data = new GLData ();
		data.doubleBuffer = true;
		final GLCanvas canvas = new GLCanvas(comp, SWT.NONE, data);

		canvas.setCurrent();
		final GLContext context = GLDrawableFactory.getFactory().createExternalGLContext();

		canvas.addListener(SWT.Resize, new Listener() {
			public void handleEvent(Event event) {
				Rectangle bounds = canvas.getBounds();
				float fAspect = (float) bounds.width / (float) bounds.height;
				canvas.setCurrent();
				context.makeCurrent();
				GL gl = context.getGL ();
				gl.glViewport(0, 0, bounds.width, bounds.height);
				gl.glMatrixMode(GL.GL_PROJECTION);
				gl.glLoadIdentity();
				GLU glu = new GLU();
				glu.gluPerspective(45.0f, fAspect, 0.5f, 400.0f);
				gl.glMatrixMode(GL.GL_MODELVIEW);
				gl.glLoadIdentity();
				context.release();
			}
		});

		context.makeCurrent();
		GL gl = context.getGL ();
		gl.glClearColor(1.0f, 1.0f, 1.0f, 1.0f);
		gl.glColor3f(1.0f, 0.0f, 0.0f);
		gl.glHint(GL.GL_PERSPECTIVE_CORRECTION_HINT, GL.GL_NICEST);
		gl.glClearDepth(1.0);
		gl.glLineWidth(2);
		gl.glEnable(GL.GL_DEPTH_TEST);
		context.release();

		comp.getDisplay().asyncExec(new Runnable() {
			int rot = 0;
			public void run() {
				if (!canvas.isDisposed()) {
					canvas.setCurrent();
					context.makeCurrent();
					GL gl = context.getGL ();
					gl.glClear(GL.GL_COLOR_BUFFER_BIT | GL.GL_DEPTH_BUFFER_BIT);
					gl.glClearColor(.3f, .5f, .8f, 1.0f);
					gl.glLoadIdentity();
					gl.glTranslatef(0.0f, 0.0f, -10.0f);
					float frot = rot;
					gl.glRotatef(0.15f * rot, 2.0f * frot, 10.0f * frot, 1.0f);
					gl.glRotatef(0.3f * rot, 3.0f * frot, 1.0f * frot, 1.0f);
					rot++;
					gl.glPolygonMode(GL.GL_FRONT_AND_BACK, GL.GL_LINE);
					gl.glColor3f(0.9f, 0.9f, 0.9f);
					drawTorus(gl, 1, 1.9f + ((float) Math.sin((0.004f * frot))), 15, 15);
					canvas.swapBuffers();
					context.release();
					comp.getDisplay().asyncExec(this);
				}
			}
		});

		while (!comp.getShell().isDisposed()) {
			if (!comp.getDisplay().readAndDispatch())
				comp.getDisplay().sleep();
		}
		comp.getDisplay().dispose();
	}
	
	private void drawTorus(GL gl, float r, float R, int nsides, int rings) {
		float ringDelta = 2.0f * (float) Math.PI / rings;
		float sideDelta = 2.0f * (float) Math.PI / nsides;
		float theta = 0.0f, cosTheta = 1.0f, sinTheta = 0.0f;
		for (int i = rings - 1; i >= 0; i--) {
			float theta1 = theta + ringDelta;
			float cosTheta1 = (float) Math.cos(theta1);
			float sinTheta1 = (float) Math.sin(theta1);
			gl.glBegin(GL.GL_QUAD_STRIP);
			float phi = 0.0f;
			for (int j = nsides; j >= 0; j--) {
				phi += sideDelta;
				float cosPhi = (float) Math.cos(phi);
				float sinPhi = (float) Math.sin(phi);
				float dist = R + r * cosPhi;
				gl.glNormal3f(cosTheta1 * cosPhi, -sinTheta1 * cosPhi, sinPhi);
				gl.glVertex3f(cosTheta1 * dist, -sinTheta1 * dist, r * sinPhi);
				gl.glNormal3f(cosTheta * cosPhi, -sinTheta * cosPhi, sinPhi);
				gl.glVertex3f(cosTheta * dist, -sinTheta * dist, r * sinPhi);
			}
			gl.glEnd();
			theta = theta1;
			cosTheta = cosTheta1;
			sinTheta = sinTheta1;
		}
	}

	

	@Override
	public void setFocus() {
		// TODO Auto-generated method stub

	}

}

Hier der Code von meinem MANIFEST:
Code:
Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: Ect Plug-in
Bundle-SymbolicName: ect; singleton:=true
Bundle-Version: 1.0.0
Bundle-Activator: ect.Activator
Bundle-Vendor: 
Require-Bundle: org.eclipse.ui,
 org.eclipse.core.runtime
Eclipse-LazyStart: true

Und hier die Fehlermeldung:
Code:
java.lang.ClassNotFoundException: javax.media.opengl.GLDrawableFactory
	at java.lang.ClassLoader.findClass(Unknown Source)
	at java.lang.ClassLoader.loadClass(Unknown Source)
	at java.lang.ClassLoader.loadClass(Unknown Source)
	at org.eclipse.osgi.framework.internal.core.BundleLoader.findClassInternal(BundleLoader.java:429)
	at org.eclipse.osgi.framework.internal.core.BundleLoader.findClass(BundleLoader.java:369)
	at org.eclipse.osgi.framework.internal.core.BundleLoader.findClass(BundleLoader.java:357)
	at org.eclipse.osgi.internal.baseadaptor.DefaultClassLoader.loadClass(DefaultClassLoader.java:83)
	at java.lang.ClassLoader.loadClass(Unknown Source)
	at java.lang.ClassLoader.loadClassInternal(Unknown Source)
	at ect.views.DiagramView.createPartControl(DiagramView.java:33)
	at org.eclipse.ui.internal.ViewReference.createPartHelper(ViewReference.java:370)
	at org.eclipse.ui.internal.ViewReference.createPart(ViewReference.java:227)
	at org.eclipse.ui.internal.WorkbenchPartReference.getPart(WorkbenchPartReference.java:592)
	at org.eclipse.ui.internal.WorkbenchPage$ActivationList.setActive(WorkbenchPage.java:4080)
	at org.eclipse.ui.internal.WorkbenchPage$17.runWithException(WorkbenchPage.java:3145)
	at org.eclipse.ui.internal.StartupThreading$StartupRunnable.run(StartupThreading.java:31)
	at org.eclipse.swt.widgets.RunnableLock.run(RunnableLock.java:35)
	at org.eclipse.swt.widgets.Synchronizer.runAsyncMessages(Synchronizer.java:123)
	at org.eclipse.swt.widgets.Display.runAsyncMessages(Display.java:3659)
	at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java:3296)
	at org.eclipse.ui.application.WorkbenchAdvisor.openWindows(WorkbenchAdvisor.java:801)
	at org.eclipse.ui.internal.Workbench$25.runWithException(Workbench.java:1342)
	at org.eclipse.ui.internal.StartupThreading$StartupRunnable.run(StartupThreading.java:31)
	at org.eclipse.swt.widgets.RunnableLock.run(RunnableLock.java:35)
	at org.eclipse.swt.widgets.Synchronizer.runAsyncMessages(Synchronizer.java:123)
	at org.eclipse.swt.widgets.Display.runAsyncMessages(Display.java:3659)
	at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java:3296)
	at org.eclipse.ui.internal.Workbench.runUI(Workbench.java:2309)
	at org.eclipse.ui.internal.Workbench.access$4(Workbench.java:2219)
	at org.eclipse.ui.internal.Workbench$4.run(Workbench.java:466)
	at org.eclipse.core.databinding.observable.Realm.runWithDefault(Realm.java:289)
	at org.eclipse.ui.internal.Workbench.createAndRunWorkbench(Workbench.java:461)
	at org.eclipse.ui.PlatformUI.createAndRunWorkbench(PlatformUI.java:149)
	at org.eclipse.ui.internal.ide.application.IDEApplication.start(IDEApplication.java:106)
	at org.eclipse.equinox.internal.app.EclipseAppHandle.run(EclipseAppHandle.java:169)
	at org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher.runApplication(EclipseAppLauncher.java:106)
	at org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher.start(EclipseAppLauncher.java:76)
	at org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseStarter.java:363)
	at org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseStarter.java:176)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
	at java.lang.reflect.Method.invoke(Unknown Source)
	at org.eclipse.equinox.launcher.Main.invokeFramework(Main.java:508)
	at org.eclipse.equinox.launcher.Main.basicRun(Main.java:447)
	at org.eclipse.equinox.launcher.Main.run(Main.java:1173)
	at org.eclipse.equinox.launcher.Main.main(Main.java:1148)

Wie gesagt: Ich denke, die Lösung besteht darin, wie man die Grafikbibliothek als Plugin zum laufen kriegen kann. Obwohl es da auch schon einige Entwicklung gab. Aber das letzte OpenGL-Plugin, was für ein Eclipse-Plugin läuft, ist die experimentelle Version 0.5, welche aber für SWT 3.2 und höher nicht zu empfehlen ist. von jogl gibt es auch eine Art SWT-JOGL-Entwciklung (opengl-swt-win32-0.7.0), jedoch gab es hier schwere View-Fehler durch die Jar-Datei org.j3d.opengl.swt.draw2d_0.7.0.jar . Habe ich nur die Datei org.j3d.opengl.swt_0.7.0.jar als dependant plugin deklariert, hat sich Eclipse wieder nicht geöffnet.
 
Hallo,

nachdem das gestern den Tag über nicht get hatte, hat es dafür aber am Abend geklappt.
Lösung ist eigentlich einfach: Die bibliotheken swt.jar, jogl.jar und gluegen-rt.jar müssen in den root des Plugins koopiert werden. Bei der Angabe des Buildpathes müssen diese libraries mit exportiert werden. Und dann noch eine wichtige Einstellung im Manifest: jogl.jar und gluegen-rt.jar müssen mit angegeben werden. Das ist klar. Es muss aber auch swt.jar im Classpath mit drinstehen, sonst funktioniert es nicht. Nur deswegen hatte es nicht geklappt
 
Zurück