如何将资源添加到类路径

发布于 2024-09-19 15:54:38 字数 4114 浏览 6 评论 0原文

如何将文件夹(例如包含 arts 的资源文件夹)添加到 netbeans 项目的类路径中?我设法通过编辑 NB 生成的项目 jar 文件(即其 MANIFEST.MF 文件 + 手动复制资源)来手动执行此操作,但应该有一种方法可以告诉 netbeans 也注意资源,不是吗?

文件夹结构如下所示:

/project/art/
/project/dist/lib/
/project/dist/art/
/project/dist/project.jar
/project/lib/
/project/src/

我不想将艺术品打包到 jar 中,因为我希望艺术品可以轻松交换。如果我将 art 文件夹添加到 src 文件夹中,那么 NB 编译正常,但 art 资源最终会出现在 jar 中。

将 art 文件夹添加到 netbeans 项目库(属性 -> 库 -> 添加 JAR/文件夹)似乎不起作用,因为最后出现错误“...\project\art 是一个目录或可以”不被阅读。不复制库。这反过来又阻止了真正的库文件夹被复制。

有什么想法吗?

此致 Chris

2 根据 gpeche 的评论做出的观察: a) 在“运行”选项卡中指定附加资源文件夹,而不是在项目属性的“编译”选项卡中指定 ->库在 Netbeans 中似乎没有太大区别(我目前使用的是 6.9.1)。输出(因此错误)保持不变,即根本没有复制任何内容:

Created dir: C:\Users\Chrisi\Desktop\vocabulary\VocabularyTrainer\dist
C:\Users\Chrisi\Desktop\vocabulary\VocabularyTrainer\art is a directory or can't be read. Not copying the libraries.
Not copying the libraries.
Building jar: C:\Users\Chrisi\Desktop\vocabulary\VocabularyTrainer\dist\VocabularyTrainer.jar

另一个有趣的方面是,在“库”面板的帮助菜单中,没有明确提及将文件夹作为库。有没有可能,Netbeans 中的按钮被错误命名,只允许真正的 jar 包?

b) 将资源文件夹添加到库列表确实会产生影响,将另一个条目添加到 MANIFEST.MF。虽然 - 这是一个较小的问题 - 类路径条目似乎总是期望资源文件夹是库文件夹的子文件夹(例如“lib/arts”),但主要问题是似乎缺少斜杠。 如前所述,在 MANIFEST.MF 中生成的 NB 条目将类似于“lib/arts”(这对我不起作用),而(手动设置)“lib/arts/”则可以?!

我使用文件夹中的资源的方式是这样的:

URL resource = getClass().getResource("/gui/refresh.png");
ImageIcon tmp = new ImageIcon(resource);

编辑:

基于Tushars评论和这篇文章 我发现以下解决方案是功能性和舒适性之间可接受的权衡。

我覆盖自动生成的“build-impl.xml”文件中的 ANT 目标,该文件在 Netbeans 项目的基本“build.xml”文件中的 MANIFEST.MF 文件中创建类路径。转到“build.xml”文件的代码如下所示:

  <property name="art.classpath" value="art/" />

  <target name="-post-jar">
    <mkdir dir="${dist.dir}/art"/>
    <copy todir="${dist.dir}/art">
      <fileset dir="${basedir}/art">
        <!-- <exclude name="**/!source/**"/> if you want to exclude something... -->
      </fileset>
    </copy>
  </target>

  <target name="-init-macrodef-copylibs">
    <macrodef name="copylibs" uri="http://www.netbeans.org/ns/j2se-project/3">
      <element name="customize" optional="true"/>
      <sequential>
        <property location="${build.classes.dir}" name="build.classes.dir.resolved"/>
        <pathconvert property="run.classpath.without.build.classes.dir">
          <path path="${run.classpath}"/>
          <map from="${build.classes.dir.resolved}" to=""/>
        </pathconvert>
        <pathconvert pathsep=" " property="jar.classpath">
          <path path="${run.classpath.without.build.classes.dir}"/>
          <chainedmapper>
            <flattenmapper/>
            <globmapper from="*" to="lib/*"/>
          </chainedmapper>
        </pathconvert>
        <taskdef classname="org.netbeans.modules.java.j2seproject.copylibstask.CopyLibs" classpath="${libs.CopyLibs.classpath}" name="copylibs"/>
        <copylibs compress="${jar.compress}" index="${jar.index}" jarfile="${dist.jar}" manifest="${manifest.file}" runtimeclasspath="${run.classpath.without.build.classes.dir}">
          <fileset dir="${build.classes.dir}"/>
          <manifest>
            <attribute name="Class-Path" value="${jar.classpath} ${art.classpath}"/>
            <customize/>
          </manifest>
        </copylibs>
      </sequential>
    </macrodef>
  </target>

权衡是,对于在 Netbeans 中进行开发,我仍然必须将资源文件夹(例如“art”)添加到库列表中以使项目在 Netbeans 中运行。这将导致 MANIFEST.MF 文件(“lib/art”)中出现一个附加条目,并导致库不会自动复制到“dist”文件夹,并显示消息“

...\art is a directory or can't be read. Not copying the libraries.
Not copying the libraries.

此行为是 - afaik - 意图(以强制所有东西都捆绑在一个罐子里),尽管关于它的讨论正在进行中。要制作真正的分发包,我必须从 NB 的库列表中删除资源文件夹并重建。

当然,关于更精简的设置而不进行任何权衡的想法仍然受到欢迎。 :)

How do you add a folder (e.g. a resource folder containing arts) to the classpath of a netbeans project? I managed to do that manually via editing the NB generated jar file of the project (that is its MANIFEST.MF file + copying the resources manually), but there should be a way to tell netbeans as well to mind the resources, no?

The folder structure looks like this:

/project/art/
/project/dist/lib/
/project/dist/art/
/project/dist/project.jar
/project/lib/
/project/src/

I don't want to package the art into the jar because I'd like the art to be easily exchangeable. If I add the art folder to the src folder then NB compiles fine, but the art resources end up in the jar.

Adding the art folder to the netbeans project libraries (Properties -> Libraries -> Add JAR/Folder) seemed not to work, because then I ended up with an error '...\project\art is a directory or can't be read. Not copying the libraries.' which in turn prevents even the real libraries folder from being copied.

Any ideas?

Best regards
Chris

2 Observations made, based on the comments from gpeche:
a) Rather specifying the additional resources folder in the "Run" tab than in the "Compile" tab of the project properties -> Libraries doesn't seem to make a lot of difference in Netbeans (I'm currently using 6.9.1). The output (and thus error) stays the same, that is nothing gets copied at all:

Created dir: C:\Users\Chrisi\Desktop\vocabulary\VocabularyTrainer\dist
C:\Users\Chrisi\Desktop\vocabulary\VocabularyTrainer\art is a directory or can't be read. Not copying the libraries.
Not copying the libraries.
Building jar: C:\Users\Chrisi\Desktop\vocabulary\VocabularyTrainer\dist\VocabularyTrainer.jar

Another interesting aspect is that in the help menu of the Libraries panel nothing is explicitly mentioned regarding folders as libraries. Could it be possible, that the button in Netbeans is falsely named, that is only real jar's are allowed?

b) Adding the resources folder to the Libraries list does have the impact though, to add another entry to the MANIFEST.MF. While - and that's the smaller issue - the classpath entry seems to be always expecting the resource folder to be a subfolder of the library folder (e.g. "lib/arts") the major problem is that there seems to be a slash missing.
As mentioned the NB generated entry in the MANIFEST.MF will look like this "lib/arts" (which does not work for me), while (manually set) "lib/arts/" does?!

The way I use resources from the folder is something like this:

URL resource = getClass().getResource("/gui/refresh.png");
ImageIcon tmp = new ImageIcon(resource);

Edit:

Based on Tushars comment and this posting I found the following solution to be an acceptable tradeoff between functionality and comfort.

I override the ANT target from the auto generated 'build-impl.xml' file which creates the Class-Path in the MANIFEST.MF file in the basic 'build.xml' file of the Netbeans project. The code which goes to the 'build.xml' file looks like this:

  <property name="art.classpath" value="art/" />

  <target name="-post-jar">
    <mkdir dir="${dist.dir}/art"/>
    <copy todir="${dist.dir}/art">
      <fileset dir="${basedir}/art">
        <!-- <exclude name="**/!source/**"/> if you want to exclude something... -->
      </fileset>
    </copy>
  </target>

  <target name="-init-macrodef-copylibs">
    <macrodef name="copylibs" uri="http://www.netbeans.org/ns/j2se-project/3">
      <element name="customize" optional="true"/>
      <sequential>
        <property location="${build.classes.dir}" name="build.classes.dir.resolved"/>
        <pathconvert property="run.classpath.without.build.classes.dir">
          <path path="${run.classpath}"/>
          <map from="${build.classes.dir.resolved}" to=""/>
        </pathconvert>
        <pathconvert pathsep=" " property="jar.classpath">
          <path path="${run.classpath.without.build.classes.dir}"/>
          <chainedmapper>
            <flattenmapper/>
            <globmapper from="*" to="lib/*"/>
          </chainedmapper>
        </pathconvert>
        <taskdef classname="org.netbeans.modules.java.j2seproject.copylibstask.CopyLibs" classpath="${libs.CopyLibs.classpath}" name="copylibs"/>
        <copylibs compress="${jar.compress}" index="${jar.index}" jarfile="${dist.jar}" manifest="${manifest.file}" runtimeclasspath="${run.classpath.without.build.classes.dir}">
          <fileset dir="${build.classes.dir}"/>
          <manifest>
            <attribute name="Class-Path" value="${jar.classpath} ${art.classpath}"/>
            <customize/>
          </manifest>
        </copylibs>
      </sequential>
    </macrodef>
  </target>

The tradeoff is that for development in Netbeans I still have to add the resource folder (e.g. 'art') to the libraries list to make the project run in Netbeans. This will cause an additional entry in the MANIFEST.MF file ('lib/art') along with the effect that the libraries will not get automatically copied to the 'dist' folder, with the message

...\art is a directory or can't be read. Not copying the libraries.
Not copying the libraries.

This behavor is - afaik - intended (to force everything to be bundled up in a jar), even though there are discussions about it going on. To make a real distribution bundle I'd have to take away the resource folder(s) from the library list in NB and rebuild.

Ideas about a more streamlined setup without any tradeoffs are of course still welcome. :)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

狼亦尘 2024-09-26 15:54:38
  1. 将资源文件夹添加到类路径:

    当您清理并构建基于 NetBeans Ant 的项目时,它会在项目的根目录中创建一个 manifest.mf 文件。该文件也包含在 JAR 文件中。修改此文件并添加条目,如下所示:

    清单版本:1.0
    X-COMMENT:主类将由构建自动添加
    班级路径:艺术/  
    

    斜杠在类路径中的 arts 之后很重要。

  2. 在发行版中包含艺术资源文件夹

    构建后将此文件夹复制到 dist 文件夹中,或者添加 ANT 目标以将所需资源复制到 dist 文件夹中。

    在 build.xml 文件中添加如下目标:

    <目标名称="-post-jar">
         >
         <复制到dir =“$ {dist.dir} / resources”>
             >
         
     
    
  3. 访问此类资源的代码:

    访问此类资源文件所需的代码应如下所示:(这在设计时不起作用,但肯定在 JAR 文件中起作用)

    //注意相对路径
    URL资源 = ClassLoader.getSystemResource("gui/refresh.png"); 
    ImageIcon tmp = new ImageIcon(资源);
    

    注意:位于项目根目录中的文件 manifest.mf 和 build.xml 可以从 NetBeans IDE 中的文件面板访问

  1. Adding resource folder to classpath:

    When you Clean-&-Build a NetBeans Ant Based Project it creates a manifest.mf file in the root directory of the project. This file gets included in the JAR file also. Modify this file and add entry like follows:

    Manifest-Version: 1.0
    X-COMMENT: Main-Class will be added automatically by build
    Class-Path: arts/  
    

    slash is important after arts in the class path.

  2. Including the arts resource folder in the distribution

    Either copy this folder in the dist folder after the build or add a ANT target to copy the required resources in the dist folder.

    Add the target like as follows in the build.xml file:

    <target name="-post-jar">
         <mkdir dir="${dist.dir}/resources"/>
         <copy todir="${dist.dir}/resources">
             <fileset dir="${basedir}/resources" />
         </copy>
     </target>
    
  3. Code to access such resources:

    The code needed to access such resource files shall be as follows: (This will not work in design time but surely from the JAR file)

    // pay attention to relative path
    URL resource = ClassLoader.getSystemResource("gui/refresh.png"); 
    ImageIcon tmp = new ImageIcon(resource);
    

    NOTE: The files manifest.mf and build.xml located in the root directory of the project are accessible from the Files Panel in NetBeans IDE

情绪操控生活 2024-09-26 15:54:38

使用 NetBeans 8.0.2:

  1. 右键单击该项目。
  2. 选择属性
  3. 选择来源
  4. 单击源包文件夹添加文件夹
  5. 选择资源所在的目录。
  6. 单击目录名称上的打开
  7. 单击确定关闭项目属性对话框。

资源已添加到项目中。

您还将看到导航窗格中添加的目录以及

在其他项目中,资源现在可用。例如,读取图像:

BufferedImage zero = ImageIO.read(OCR.class.getResourceAsStream("/0.bmp"));

Using NetBeans 8.0.2:

  1. Right-click the project.
  2. Select Properties.
  3. Select Sources.
  4. Click Add Folder for the Source Package Folders.
  5. Select the the directory where the resources exist.
  6. Click Open on the directory name.
  7. Click OK to close the Project Properties dialog.

The resources are added to the project.

You'll see the directory added in your Navigation pane as well

In the other project, the resources are now available. For example, to read an image:

BufferedImage zero = ImageIO.read(OCR.class.getResourceAsStream("/0.bmp"));
雨夜星沙 2024-09-26 15:54:38

为了从类路径中删除 lib/art 并且不得到“是目录或无法读取”,需要从路径中删除 lib/art:

    <pathconvert property="run.classpath.without.build.classes.dir">
      <path path="${run.classpath}"/>
      <map from="${build.classes.dir.resolved}" to=""/>
      **<map from="${basedir}/art" to=""/> <!-- remove art from lib -->**
    </pathconvert>

In order to remove the lib/art from Class-Path and not get "is a directory or can't be read" need delete lib/art from path:

    <pathconvert property="run.classpath.without.build.classes.dir">
      <path path="${run.classpath}"/>
      <map from="${build.classes.dir.resolved}" to=""/>
      **<map from="${basedir}/art" to=""/> <!-- remove art from lib -->**
    </pathconvert>
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文