Java:为什么打包到jar文件中的代码会阻止外部类访问?
我的Java应用程序有一个插件系统。我使用URL类加载器调用外部类。当我的应用程序以类文件的形式运行时,以及当我的应用程序以JAR形式运行时,这一部分都工作得很好。我遇到的问题是,插件文件可以运行自己的独立代码,但是它们创建了一个JPanel。当我尝试将该JPanel添加到主应用程序类中的JPanel时,我得到一个引用主类的空指针异常。(com.cpcookieman.app.Main)但如果我运行应用程序的类文件,则不会发生这种情况,只有当它打包后才会发生。我怎样才能解决这个问题 为什么我的代码被打包到jar文件中会阻止外部类访问jar中的类 编辑:根据请求,堆栈跟踪Java:为什么打包到jar文件中的代码会阻止外部类访问?,java,eclipse,swing,jar,classloader,Java,Eclipse,Swing,Jar,Classloader,我的Java应用程序有一个插件系统。我使用URL类加载器调用外部类。当我的应用程序以类文件的形式运行时,以及当我的应用程序以JAR形式运行时,这一部分都工作得很好。我遇到的问题是,插件文件可以运行自己的独立代码,但是它们创建了一个JPanel。当我尝试将该JPanel添加到主应用程序类中的JPanel时,我得到一个引用主类的空指针异常。(com.cpcookieman.app.Main)但如果我运行应用程序的类文件,则不会发生这种情况,只有当它打包后才会发生。我怎样才能解决这个问题 为什么我的代
java.lang.NullPointerException
at TestPlugin2.Main.<init>(Main.java:23)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source)
at java.lang.reflect.Constructor.newInstance(Unknown Source)
at java.lang.Class.newInstance0(Unknown Source)
at java.lang.Class.newInstance(Unknown Source)
at com.cpcookieman.ph.PluginLoader$2.run(PluginLoader.java:74)
at java.lang.Thread.run(Unknown Source)
插件使用它的构造函数加载,并创建一个面板添加到JAR文件中一个类内部的框架中。JAR是主要的应用程序,如果有人对此感到困惑的话。我真的不知道您的项目的结构,尽管我已经为您制作了一个小的示例代码,让您看一看 假设我的项目位于
C:\Mine\JAVA\J2SE\src\testingjar>
我的目录结构如下所示:
testingjar
|
----------------------------------
| | | |
classes src manifest.text test.jar(this .jar we be creating shortly)
| |
| (Almost same as classes folder, just .java files)
---------------
| |
actualtest test
| |
*.class *.class
package test;
import java.awt.*;
import javax.swing.*;
public class CustomPanel extends JPanel
{
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
}
我的类将成为.jar文件的一部分,如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomPanel extends JPanel
{
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
}
我用以下命令编译了这个类:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
现在正在为JAR文件创建清单文件,其内容如下:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
请记住冒号(:)和软件包名称(即test)之间的空格,在CustomPanel之后,按Enter键并保存文件。
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
现在,为了创建名为test.JAR
的JAR文件,我编写了以下命令:
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
现在将使用此.jar文件的类如下所示:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
我通过编写以下命令编译了它:
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\ActualImplement
ation.java
现在要运行,我编写了以下命令:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
输出
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
一定要配合这些步骤,可能你遗漏了什么,因为它在我这边工作得很好
最新编辑:正如所问,我是以另一种方式编辑的,现在JFrame
在.jar文件中,JPanel
正在使用它。
将成为.jar文件一部分的类如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomFrame extends JFrame
{
public CustomFrame(String title)
{
super(title);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
}
package actualtest;
import test.CustomFrame;
import java.awt.*;
import javax.swing.*;
// http://stackoverflow.com/a/11150286/1057230
public class CustomPanel extends JPanel
{
private CustomFrame frame;
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
private void createAndDisplayGUI()
{
frame = new CustomFrame("Testing Jar Implementation");
frame.setContentPane(this);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new CustomPanel().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomFrame.java
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\CustomPanel.jav
a
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.CustomPanel
manifest.txt文件的内容将更改如下:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
将使用.jar文件中的CustomFrame类的类如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomFrame extends JFrame
{
public CustomFrame(String title)
{
super(title);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
}
package actualtest;
import test.CustomFrame;
import java.awt.*;
import javax.swing.*;
// http://stackoverflow.com/a/11150286/1057230
public class CustomPanel extends JPanel
{
private CustomFrame frame;
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
private void createAndDisplayGUI()
{
frame = new CustomFrame("Testing Jar Implementation");
frame.setContentPane(this);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new CustomPanel().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomFrame.java
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\CustomPanel.jav
a
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.CustomPanel
编译顺序与之前非常相同,如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomFrame extends JFrame
{
public CustomFrame(String title)
{
super(title);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
}
package actualtest;
import test.CustomFrame;
import java.awt.*;
import javax.swing.*;
// http://stackoverflow.com/a/11150286/1057230
public class CustomPanel extends JPanel
{
private CustomFrame frame;
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
private void createAndDisplayGUI()
{
frame = new CustomFrame("Testing Jar Implementation");
frame.setContentPane(this);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new CustomPanel().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomFrame.java
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\CustomPanel.jav
a
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.CustomPanel
我得到的仍然是相同的输出
最新编辑:
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\ActualImplement
ation.java
我刚刚发现,有时候这个方法是有效的,而不是后者,当使用JAR文件时,必须指定包含点运算符的类路径,比如
C:\Mine\JAVA\J2SE\src\testingjar>java -classpath test.jar;.; actualtest.CustomPanel
这是当我将
actualtest
包
放在testingjar
文件夹中时,上面的命令适用于这种情况。我真的不知道您项目的结构,尽管我已经为您制作了一个小示例代码,请看
假设我的项目位于C:\Mine\JAVA\J2SE\src\testingjar>
我的目录结构如下所示:
testingjar
|
----------------------------------
| | | |
classes src manifest.text test.jar(this .jar we be creating shortly)
| |
| (Almost same as classes folder, just .java files)
---------------
| |
actualtest test
| |
*.class *.class
package test;
import java.awt.*;
import javax.swing.*;
public class CustomPanel extends JPanel
{
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
}
我的类将成为.jar文件的一部分,如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomPanel extends JPanel
{
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
}
我用以下命令编译了这个类:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
现在正在为JAR文件创建清单文件,其内容如下:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
请记住冒号(:)和软件包名称(即test)之间的空格,在CustomPanel之后,按Enter键并保存文件。
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
现在,为了创建名为test.JAR
的JAR文件,我编写了以下命令:
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
现在将使用此.jar文件的类如下所示:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
我通过编写以下命令编译了它:
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\ActualImplement
ation.java
现在要运行,我编写了以下命令:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
输出
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
一定要配合这些步骤,可能你遗漏了什么,因为它在我这边工作得很好
最新编辑:正如所问,我是以另一种方式编辑的,现在JFrame
在.jar文件中,JPanel
正在使用它。
将成为.jar文件一部分的类如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomFrame extends JFrame
{
public CustomFrame(String title)
{
super(title);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
}
package actualtest;
import test.CustomFrame;
import java.awt.*;
import javax.swing.*;
// http://stackoverflow.com/a/11150286/1057230
public class CustomPanel extends JPanel
{
private CustomFrame frame;
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
private void createAndDisplayGUI()
{
frame = new CustomFrame("Testing Jar Implementation");
frame.setContentPane(this);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new CustomPanel().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomFrame.java
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\CustomPanel.jav
a
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.CustomPanel
manifest.txt文件的内容将更改如下:
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomPanel.java
Main-Class: test.CustomPanel
package actualtest;
import test.CustomPanel;
import java.awt.*;
import javax.swing.*;
public class ActualImplementation
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Testing Jar Implementation");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
CustomPanel panel = new CustomPanel();
frame.setContentPane(panel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ActualImplementation().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.ActualImplementation
Main-Class: test.CustomFrame
将使用.jar文件中的CustomFrame类的类如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomFrame extends JFrame
{
public CustomFrame(String title)
{
super(title);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
}
package actualtest;
import test.CustomFrame;
import java.awt.*;
import javax.swing.*;
// http://stackoverflow.com/a/11150286/1057230
public class CustomPanel extends JPanel
{
private CustomFrame frame;
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
private void createAndDisplayGUI()
{
frame = new CustomFrame("Testing Jar Implementation");
frame.setContentPane(this);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new CustomPanel().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomFrame.java
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\CustomPanel.jav
a
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.CustomPanel
编译顺序与之前非常相同,如下所示:
package test;
import java.awt.*;
import javax.swing.*;
public class CustomFrame extends JFrame
{
public CustomFrame(String title)
{
super(title);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
}
package actualtest;
import test.CustomFrame;
import java.awt.*;
import javax.swing.*;
// http://stackoverflow.com/a/11150286/1057230
public class CustomPanel extends JPanel
{
private CustomFrame frame;
public CustomPanel()
{
setOpaque(true);
setBackground(Color.DARK_GRAY);
JLabel label = new JLabel(
"I am a JLabel from Java Swing", JLabel.CENTER);
label.setOpaque(false);
label.setForeground(Color.WHITE);
add(label);
}
private void createAndDisplayGUI()
{
frame = new CustomFrame("Testing Jar Implementation");
frame.setContentPane(this);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
@Override
public Dimension getPreferredSize()
{
return (new Dimension(500, 300));
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new CustomPanel().createAndDisplayGUI();
}
});
}
}
C:\Mine\JAVA\J2SE\src\testingjar>javac -d classes src\test\CustomFrame.java
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>jar -cfm ..\test.jar ..\manifest.txt test
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\CustomPanel.jav
a
C:\Mine\JAVA\J2SE\src\testingjar>cd classes
C:\Mine\JAVA\J2SE\src\testingjar\classes>java actualtest.CustomPanel
我得到的仍然是相同的输出
最新编辑:
C:\Mine\JAVA\J2SE\src\testingjar\classes>cd..
C:\Mine\JAVA\J2SE\src\testingjar>javac -classpath test.jar -d classes src\actualtest\ActualImplement
ation.java
我刚刚发现,有时候这个方法是有效的,而不是后者,当使用JAR文件时,必须指定包含点运算符的类路径,比如
C:\Mine\JAVA\J2SE\src\testingjar>java -classpath test.jar;.; actualtest.CustomPanel
这是当我将
actualtest
包
放入testingjar
文件夹中时,上面的命令对这种情况有效。“Wut”?也许他们在CP中没有JAR?(然而,在大多数情况下,NPE是一个不同的问题……因为类加载失败会导致严重的非NPE异常,这通常会杀死VM。也许可以研究一下,而不是责怪类加载器/加载:-)JAR是否需要放在某个文件夹中才能放在类路径中?如果是这样,JAR是否可以自我调整以将自己放入类路径中?JAR必须位于类路径中;它不能把自己放在那里。(还要确保没有/没有使用过时版本的类…因为这可能是一件令人讨厌的事情。)你能发布堆栈跟踪吗?你必须发布一些代码,从TestPlugin2.Main.java开始。更好的是w