【问题标题】:What's the best way to start Java applications on Windows 7?在 Windows 7 上启动 Java 应用程序的最佳方式是什么?
【发布时间】:2012-03-08 23:14:34
【问题描述】:

要求

我想在 Windows 7 上发布一个 Java GUI 应用程序。该应用程序使用 Swing Toolkit,不需要任何本机代码。该应用程序是使用NSIS 安装程序安装的。我想尽可能好地将这个应用程序集成到 Windows 7 中。这意味着:

  • 当应用程序运行时,必须能够将应用程序固定到任务栏。
  • 必须可以将数据文件与应用程序相关联,以便 Windows 使用我的应用程序打开这些文件。
  • 必须自动使用 32 位 Java 运行时和 64 位 Java 运行时。因此,当用户卸载 32 位 Java 并安装 64 位 Java(反之亦然)时,我的应用程序必须仍然可以工作。
  • 必须支持 Windows 的大字体设置。我不是很了解这个功能。我只知道有些应用程序完全忽略它,其他应用程序(如谷歌浏览器)是像素缩放的(看起来真的很难看),而其他应用程序则通过按预期使用更大的字体来支持它(这就是我想要的,通常它可以工作。只有 WinRun4J 解决方案下面提到的不适用于它)。

经过测试的解决方案

WinRun4J

WinRun4j 是一个启动 Java 应用程序的 EXE 文件。因为应用程序没有派生新的 Java 进程,Windows 认为 EXE 文件就是应用程序。所以任务栏没有问题。文件关联有效,因为文件可以简单地与 EXE 文件关联。

问题:

  • 不支持大字体。应用程序窗口改为像素缩放(如 Google Chrome)。
  • 根据安装的 JRE,必须使用两个不同的 EXE 文件。因此,当安装 64 位 JRE 时,必须使用 64 位 EXE 文件启动应用程序。安装 32 位 JRE 插件时,必须使用其他 EXE。这对用户不友好,因为用户不明白为什么在只安装 32 位 JRE 的情况下必须在 64 位操作系统上使用 32 位 EXE。

Launch4J

Launch4J 创建一个 32 位 EXE,它启动一个外部 Java 进程来启动 Java 应用程序。所以与 WinRun4J 不同,它也可以启动 64 位 Java。

问题:

  • 无法将应用程序固定到任务栏。
  • 如果是headerType="gui"System.out.println 将不会打印到控制台,无论应用程序是否从控制台启动。

罐子

在 Windows 上,您只需双击 JAR 文件即可启动应用程序。安装的 JRE 没关系,简单有效。但是……

问题:

  • 应用程序无法固定到任务栏。
  • 无法在开始菜单中创建快捷方式。
  • 无法将文件与 JAR 文件相关联。

BAT/CMD

可以使用像这样的简单批处理文件来启动应用程序:

@echo off
start c:\windows\system32\javaw.exe -jar "c:\program files\myapp\myapp.jar" %1

可以为此批处理文件创建快捷方式来设置自定义图标。

问题:

  • 应用程序启动时会弹出一个 DOS 窗口。
  • 批处理文件不知道 javaw.exe 的位置。根据安装的 java 版本(32 位或 64 位),它可能位于 c:\windows\syswow64,而 Windows 不会自动从批处理文件重定向此调用。使用 JAVA_HOME 环境变量也是不行的,因为 Java 不会自动设置它。
  • 将文件与批处理文件关联时,无法设置自定义图标。
  • 任务栏支持无法正常工作。手动启动批处理文件时,可以将应用程序固定到它,但是当双击关联文件时,它就不起作用了。

快捷方式

可以只创建一个快捷方式来启动应用程序,而不是使用批处理文件。它链接到这个命令:c:\windows\system32\javaw.exe -jar "c:\program files\myapp\myapp.jar"。如果安装了 32 位 Java JRE,Windows 会自动将此调用重定向到 SysWOW64 目录。

问题:

  • 无法将文件与其关联,因为 Windows 仅接受 EXE/COM/PIF/BAT/CMD 文件作为关联目标。 LNK 文件不起作用。

问题

是否有其他解决方案可以满足上述所有要求?或者是否有任何技巧可以解决上述解决方案的问题?

解决方案

在使用Launch4j 解决了任务栏固定问题之后,看起来是最好的解决方案。 Launch4j 可以很容易地集成到 Maven 项目中(使用 thisthis 插件),配置非常简单,除了任务栏固定之外,一切都可以开箱即用。对于任务栏固定,Java 应用程序必须设置 appModelUserId,如this question 的答案中所述。

此外,Java 应用程序必须由安装程序安装,该安装程序必须至少安装一个指向 EXE 的快捷方式。此快捷方式还必须包含 appModelUserId。使用 NSIS,这可以通过 WinShell plugin 和如下配置来完成:

CreateShortCut "$SMPROGRAMS\MyApp.lnk" \
    "$INSTDIR\myapp.exe" "" "$INSTDIR\myapp.exe" 0 SW_SHOWNORMAL
WinShell::SetLnkAUMI "$SMPrograms\MyApp.lnk" "MyAppModelUserId"

由于某些未知的原因,这个快捷方式只需要存在。你不必使用它。您可以双击 EXE 并且任务栏固定仍然有效。您甚至可以在应用程序文件夹的某个子文件夹中创建快捷方式。删除 EXE 文件的最后一个快捷方式后,任务栏固定停止工作。

【问题讨论】:

  • "根据安装的 JRE,必须使用两个不同的 EXE 文件"。这对用户来说真的那么可怕吗?几乎所有为 x86 和 x64 系统分发的软件都迫使用户决定下载/安装/启动什么。我知道 Sysinternals ProcessExplorer 在两个平台上都从一个 exe 运行,但它们只是将 x64 版本打包到 x86 中。另外,看看Lau​​nch4j,也许它会满足你的要求。
  • @Mersenne:当这个决定取决于操作系统时,这不是问题。但在这种情况下,它取决于安装的 JRE,这是一个问题。用户下载 64 位版本的应用程序是因为他们拥有 64 位 Windows。然后他们抱怨应用程序无法运行,因为他们的 Windows 是由一些硬件供应商预安装的 32 位 Java。即使他们选择了 32 位应用程序(或者安装程序自动做出此决定),当用户将 32 位 JRE 替换为 64 位 JRE 时,应用程序仍然会中断。
  • 是的,这是一个真正的问题:(我们可以将 JRE 视为我们的应用程序所需的一堆库。不兼容的库 -> 应用程序无法运行。但对于用户来说,它并不那么清楚。

标签: java windows batch-file launch4j winrun4j


【解决方案1】:

试试 Launch4j (http://launch4j.sourceforge.net/),它是一个简单的 jar 到 exe 包装器(实际上包装 jar 是可选的)。它应该可以解决您的图标和任务栏要求。它还能够定位已安装的 JRE(一些可配置的规则)。我不太明白的字体问题,Swing 应该根据 Windows 设置自动使用字体,除非你在 JRE 选项或代码中以某种方式覆盖它。

【讨论】:

  • 是的,Java本身对大字体没有问题。字体被很好地放大,扩大了整个布局,Swing 应用程序仍然可以完美运行。但是当使用 WinRun4J 启动应用程序时,windows 似乎将 Swing 框架的输出缩放为位图。因此,您看起来像是在 1650x1050 显示器上运行 1280x800 桌面。一切都是像素缩放的(带抗锯齿)。
  • 我刚试过 Launch4J。无法将应用程序固定到任务栏。我是否包装 JAR 都没关系。
  • 有一个选项“自定义进程名称和 XP 样式 mainfest”(在第一个选项卡上),我认为应该可以解决问题。
  • 这篇博文声称它依赖于 .EXE 名称,因为我们这里没有 Win7,所以无法尝试:west-wind.com/weblog/posts/2009/Oct/08/…
  • 我很确定我的应用程序名称不是保留名称。但是我尝试将其重命名为一些随机的 wkjbskdfjbnwer.exe,但没有帮助:-)
【解决方案2】:

Java Web Start - 这些天我不会考虑以任何其他方式分发应用程序。

用户确实需要至少有 J2SE 1.4;如果您的应用程序需要更高版本,Web Start 将自动下载相应的 JRE。

有关桌面集成(shortcutoffline-allowed)和文件关联(association)的标签,请参阅JNLP 参考。不过,这些仅在 WS 1.5 中受支持。

【讨论】:

  • 你能提供一个像这样分布的不错的应用程序的链接,以便我可以轻松地检查它的感觉吗?当用户尚未安装 Java 时会发生什么?如果需要,安装程序可以自动下载和安装 JRE,但它如何与 WebStart 一起使用?
  • @kayahr :希望Wikipedia 可以帮助你。查看众所周知的应用程序。关于Web Start的更多信息
  • @kayahr Java 教程中充满了 Java Web Start 示例,例如:docs.oracle.com/javase/tutorial/ui/overview/demo.html
  • 但是要求呢:是否可以将 Web Start 应用程序固定到任务栏?您能否将文件扩展名与应用程序相关联,以便通过双击数据文件启动应用程序?我不这么认为。但也许我错了?
  • @kayahr:支持文件关联,请参阅我的编辑。恐怕我不知道它在固定时的行为(快速谷歌搜索表明它可能有问题)。我不在 Windows 7 上 - 为什么不尝试使用其中一个示例应用程序呢?
【解决方案3】:

我个人使用 Launch4j(更准确地说是通过带有 maven-launch4j-plugin 的 maven),并且我在我的应用程序中实现了系统托盘管理...(参见 http://java.sun.com/developer/technicalArticles/J2SE/Desktop/javase6/systemtray/ )。

【讨论】:

  • 托盘不在我的列表要求中。我以前用过它,它可以工作(除了图标的一些透明度问题)。它与 java 应用程序的启动方式无关。它总是一样的。
  • 绝对...对不起。当您谈到任务栏上的固定问题时,我以为您实际上指的是系统托盘...(我不是 Windows 7 用户...:)。
  • 我在问题文本中将“Windows”更改为“Windows 7”以使其更清晰。在其他 Windows 版本上,“固定”不是问题,因为它不受支持。其他要求在所有 Windows 版本上都相同。
【解决方案4】:

总体而言,我在 WinRun4J 方面取得了不错的成功,但我在字体方面做得并不多,所以我承认我不确定我是否理解你为什么会遇到你所描述的问题。

但是,根据您的描述,听起来您对 Java 原生启动器有非常具体的要求。为什么不自己写呢?您可以从 WinRun4J(它是开源的,在 Eclipse CPL 下获得许可)之类的东西开始,然后根据您的需要对其进行修改。

或者,您可以查看其他程序使用的本机启动器。 Eclipse 和 NetBeans 启动器似乎都运行良好,而且都是开源的。你也可以很容易地适应其中之一。

【讨论】:

  • 我在 Windows 上尝试了 Eclipse 和 Netbeans。结果:他们遇到了我要解决的相同问题:他们无法固定到任务栏。右键单击图标只显示“关闭应用程序”,没有固定。手动将启动器图标拖到任务栏中是可行的,但是当单击这些启动器时,任务栏中会出现第二个图标。
  • 那是因为进程没有设置AppUserModelID。
【解决方案5】:

顺便说一句,还可以查看将您的应用放入工具托盘/系统托盘的新功能:

Oracle 有一个关于如何使用系统托盘的tutorial

这与 Java SE 6 相关....让我也想知道在较新的 Java 7 中可能还有哪些其他好东西?

【讨论】:

  • 使用托盘并不是很好地集成到 Windows 中的必要条件。托盘只能用于通知,不幸的是它被许多应用程序误用于其他目的。我的应用程序不需要通知,所以我不需要托盘。但是当我需要它时,使用它是没有问题的,与我启动应用程序的方式无关。
猜你喜欢
  • 1970-01-01
  • 2015-01-07
  • 2021-07-01
  • 2011-04-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-10-26
  • 1970-01-01
相关资源
最近更新 更多