diff options
Diffstat (limited to 'launcher')
| -rw-r--r-- | launcher/CMakeLists.txt | 23 | ||||
| -rw-r--r-- | launcher/MCFrame.java | 123 | ||||
| -rw-r--r-- | launcher/MultiMCLauncher.java | 331 | ||||
| -rw-r--r-- | launcher/UseJava.cmake | 881 | ||||
| -rw-r--r-- | launcher/UseJavaClassFilelist.cmake | 52 | ||||
| -rw-r--r-- | launcher/UseJavaSymlinks.cmake | 32 | ||||
| -rw-r--r-- | launcher/net/minecraft/Launcher.java | 154 | ||||
| -rw-r--r-- | launcher/org/simplericity/macify/eawt/Application.java | 176 | ||||
| -rw-r--r-- | launcher/org/simplericity/macify/eawt/ApplicationAdapter.java | 48 | ||||
| -rw-r--r-- | launcher/org/simplericity/macify/eawt/ApplicationEvent.java | 25 | ||||
| -rw-r--r-- | launcher/org/simplericity/macify/eawt/ApplicationListener.java | 27 | ||||
| -rw-r--r-- | launcher/org/simplericity/macify/eawt/DefaultApplication.java | 418 |
12 files changed, 2290 insertions, 0 deletions
diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt new file mode 100644 index 00000000..7f189458 --- /dev/null +++ b/launcher/CMakeLists.txt @@ -0,0 +1,23 @@ +cmake_minimum_required(VERSION 2.8.6) +project(launcher Java) +set(CMAKE_MODULE_PATH "${PROJECT_SOURCE_DIR}") +find_package(Java 1.6 REQUIRED COMPONENTS Development) + + +include(UseJava) +set(CMAKE_JAVA_JAR_ENTRY_POINT MultiMCLauncher) +set(CMAKE_JAVA_COMPILE_FLAGS -target 1.6 -source 1.6 -Xlint:deprecation -Xlint:unchecked) +set(CMAKE_JAVA_TARGET_OUTPUT_DIR "${PROJECT_SOURCE_DIR}/../resources") + +set(SRC + MultiMCLauncher.java + org/simplericity/macify/eawt/Application.java + org/simplericity/macify/eawt/ApplicationAdapter.java + org/simplericity/macify/eawt/ApplicationEvent.java + org/simplericity/macify/eawt/ApplicationListener.java + org/simplericity/macify/eawt/DefaultApplication.java + net/minecraft/Launcher.java + MCFrame.java +) + +add_jar(MultiMCLauncher ${SRC})
\ No newline at end of file diff --git a/launcher/MCFrame.java b/launcher/MCFrame.java new file mode 100644 index 00000000..d6ebb240 --- /dev/null +++ b/launcher/MCFrame.java @@ -0,0 +1,123 @@ +// +// Copyright 2012 MultiMC Contributors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// + +import net.minecraft.Launcher; +import java.applet.Applet; +import java.awt.Dimension; +import java.awt.Frame; +import java.awt.Toolkit; +import java.awt.event.WindowEvent; +import java.awt.event.WindowListener; +import java.net.MalformedURLException; +import java.net.URL; +import java.io.IOException; +import java.io.File; +import javax.imageio.ImageIO; +import java.awt.image.BufferedImage; + +public class MCFrame extends Frame implements WindowListener +{ + private Launcher appletWrap = null; + public MCFrame(String title) + { + super(title); + BufferedImage image = null; + try + { + image = ImageIO.read(new File("icon.png")); + setIconImage(image); + } + catch (IOException e) + { + e.printStackTrace(); + } + this.addWindowListener(this); + } + + public void start(Applet mcApplet, String user, String session, Dimension winSize, boolean maximize) + { + try + { + appletWrap = new Launcher(mcApplet, new URL("http://www.minecraft.net/game")); + } + catch (MalformedURLException ignored){} + + appletWrap.setParameter("username", user); + appletWrap.setParameter("sessionid", session); + appletWrap.setParameter("stand-alone", "true"); // Show the quit button. + mcApplet.setStub(appletWrap); + + this.add(appletWrap); + appletWrap.setPreferredSize(winSize); + this.pack(); + this.setLocationRelativeTo(null); + this.setResizable(true); + if (maximize) + this.setExtendedState(MAXIMIZED_BOTH); + + validate(); + appletWrap.init(); + appletWrap.start(); + setVisible(true); + } + + @Override + public void windowActivated(WindowEvent e) {} + + @Override + public void windowClosed(WindowEvent e) {} + + @Override + public void windowClosing(WindowEvent e) + { + new Thread() + { + public void run() + { + try + { + Thread.sleep(30000L); + } catch (InterruptedException localInterruptedException) + { + localInterruptedException.printStackTrace(); + } + System.out.println("FORCING EXIT!"); + System.exit(0); + } + } + .start(); + + if (appletWrap != null) + { + appletWrap.stop(); + appletWrap.destroy(); + } + // old minecraft versions can hang without this >_< + System.exit(0); + } + + @Override + public void windowDeactivated(WindowEvent e) {} + + @Override + public void windowDeiconified(WindowEvent e) {} + + @Override + public void windowIconified(WindowEvent e) {} + + @Override + public void windowOpened(WindowEvent e) {} +}
\ No newline at end of file diff --git a/launcher/MultiMCLauncher.java b/launcher/MultiMCLauncher.java new file mode 100644 index 00000000..09a019ce --- /dev/null +++ b/launcher/MultiMCLauncher.java @@ -0,0 +1,331 @@ +// +// Copyright 2012 MultiMC Contributors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// + +import java.applet.Applet; +import java.awt.Dimension; + +import java.io.File; +import java.io.IOException; +import java.lang.reflect.Field; +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Modifier; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.URLClassLoader; +import java.util.ArrayList; +import java.util.Enumeration; +import java.util.zip.ZipEntry; +import java.util.zip.ZipException; +import java.util.zip.ZipFile; + +import javax.imageio.ImageIO; +import java.awt.image.BufferedImage; +import org.simplericity.macify.eawt.Application; +import org.simplericity.macify.eawt.DefaultApplication; + +public class MultiMCLauncher +{ + /** + * @param args + * The arguments you want to launch Minecraft with. New path, + * Username, Session ID. + */ + public static void main(String[] args) + { + if (args.length < 3) + { + System.out.println("Not enough arguments."); + System.exit(-1); + } + + // Set the OSX application icon first, if we are on OSX. + Application application = new DefaultApplication(); + if(application.isMac()) + { + try + { + BufferedImage image = ImageIO.read(new File("icon.png")); + application.setApplicationIconImage(image); + } + catch (IOException e) + { + e.printStackTrace(); + } + } + + String userName = args[0]; + String sessionId = args[1]; + String windowtitle = args[2]; + String windowParams = args[3]; + String lwjgl = args[4]; + String cwd = System.getProperty("user.dir"); + + Dimension winSize = new Dimension(854, 480); + boolean maximize = false; + boolean compatMode = false; + + + String[] dimStrings = windowParams.split("x"); + + if (windowParams.equalsIgnoreCase("compatmode")) + { + compatMode = true; + } + else if (windowParams.equalsIgnoreCase("max")) + { + maximize = true; + } + else if (dimStrings.length == 2) + { + try + { + winSize = new Dimension(Integer.parseInt(dimStrings[0]), + Integer.parseInt(dimStrings[1])); + } + catch (NumberFormatException e) + { + System.out.println("Invalid Window size argument, " + + "using default."); + } + } + else + { + System.out.println("Invalid Window size argument, " + + "using default."); + } + + try + { + File binDir = new File(cwd, "bin"); + File lwjglDir; + if(lwjgl.equalsIgnoreCase("Mojang")) + lwjglDir = binDir; + else + lwjglDir = new File(lwjgl); + + System.out.println("Loading jars..."); + String[] lwjglJars = new String[] { + "lwjgl.jar", "lwjgl_util.jar", "jinput.jar" + }; + + URL[] urls = new URL[4]; + try + { + File f = new File(binDir, "minecraft.jar"); + urls[0] = f.toURI().toURL(); + System.out.println("Loading URL: " + urls[0].toString()); + + for (int i = 1; i < urls.length; i++) + { + File jar = new File(lwjglDir, lwjglJars[i-1]); + urls[i] = jar.toURI().toURL(); + System.out.println("Loading URL: " + urls[i].toString()); + } + } + catch (MalformedURLException e) + { + System.err.println("MalformedURLException, " + e.toString()); + System.exit(5); + } + + System.out.println("Loading natives..."); + String nativesDir = new File(lwjglDir, "natives").toString(); + + System.setProperty("org.lwjgl.librarypath", nativesDir); + System.setProperty("net.java.games.input.librarypath", nativesDir); + + URLClassLoader cl = + new URLClassLoader(urls, MultiMCLauncher.class.getClassLoader()); + + // Get the Minecraft Class. + Class<?> mc = null; + try + { + mc = cl.loadClass("net.minecraft.client.Minecraft"); + + Field f = getMCPathField(mc); + + if (f == null) + { + System.err.println("Could not find Minecraft path field. Launch failed."); + System.exit(-1); + } + + f.setAccessible(true); + f.set(null, new File(cwd)); + // And set it. + System.out.println("Fixed Minecraft Path: Field was " + f.toString()); + } + catch (ClassNotFoundException e) + { + System.err.println("Can't find main class. Searching..."); + + // Look for any class that looks like the main class. + File mcJar = new File(new File(cwd, "bin"), "minecraft.jar"); + ZipFile zip = null; + try + { + zip = new ZipFile(mcJar); + } catch (ZipException e1) + { + e1.printStackTrace(); + System.err.println("Search failed."); + System.exit(-1); + } catch (IOException e1) + { + e1.printStackTrace(); + System.err.println("Search failed."); + System.exit(-1); + } + + Enumeration<? extends ZipEntry> entries = zip.entries(); + ArrayList<String> classes = new ArrayList<String>(); + + while (entries.hasMoreElements()) + { + ZipEntry entry = entries.nextElement(); + if (entry.getName().endsWith(".class")) + { + String entryName = entry.getName().substring(0, entry.getName().lastIndexOf('.')); + entryName = entryName.replace('/', '.'); + System.out.println("Found class: " + entryName); + classes.add(entryName); + } + } + + for (String clsName : classes) + { + try + { + Class<?> cls = cl.loadClass(clsName); + if (!Runnable.class.isAssignableFrom(cls)) + { + continue; + } + else + { + System.out.println("Found class implementing runnable: " + + cls.getName()); + } + + if (getMCPathField(cls) == null) + { + continue; + } + else + { + System.out.println("Found class implementing runnable " + + "with mcpath field: " + cls.getName()); + } + + mc = cls; + break; + } + catch (ClassNotFoundException e1) + { + // Ignore + continue; + } + } + + if (mc == null) + { + System.err.println("Failed to find Minecraft main class."); + System.exit(-1); + } + else + { + System.out.println("Found main class: " + mc.getName()); + } + } + + System.setProperty("minecraft.applet.TargetDirectory", cwd); + + String[] mcArgs = new String[2]; + mcArgs[0] = userName; + mcArgs[1] = sessionId; + + if (compatMode) + { + System.out.println("Launching in compatibility mode..."); + mc.getMethod("main", String[].class).invoke(null, (Object) mcArgs); + } + else + { + System.out.println("Launching with applet wrapper..."); + try + { + Class<?> MCAppletClass = cl.loadClass( + "net.minecraft.client.MinecraftApplet"); + Applet mcappl = (Applet) MCAppletClass.newInstance(); + MCFrame mcWindow = new MCFrame(windowtitle); + mcWindow.start(mcappl, userName, sessionId, winSize, maximize); + } catch (InstantiationException e) + { + System.out.println("Applet wrapper failed! Falling back " + + "to compatibility mode."); + mc.getMethod("main", String[].class).invoke(null, (Object) mcArgs); + } + } + } catch (ClassNotFoundException e) + { + e.printStackTrace(); + System.exit(1); + } catch (IllegalArgumentException e) + { + e.printStackTrace(); + System.exit(2); + } catch (IllegalAccessException e) + { + e.printStackTrace(); + System.exit(2); + } catch (InvocationTargetException e) + { + e.printStackTrace(); + System.exit(3); + } catch (NoSuchMethodException e) + { + e.printStackTrace(); + System.exit(3); + } catch (SecurityException e) + { + e.printStackTrace(); + System.exit(4); + } + } + + public static Field getMCPathField(Class<?> mc) + { + Field[] fields = mc.getDeclaredFields(); + + for (int i = 0; i < fields.length; i++) + { + Field f = fields[i]; + if (f.getType() != File.class) + { + // Has to be File + continue; + } + if (f.getModifiers() != (Modifier.PRIVATE + Modifier.STATIC)) + { + // And Private Static. + continue; + } + return f; + } + return null; + } +} diff --git a/launcher/UseJava.cmake b/launcher/UseJava.cmake new file mode 100644 index 00000000..1a5ef107 --- /dev/null +++ b/launcher/UseJava.cmake @@ -0,0 +1,881 @@ +# - Use Module for Java +# This file provides functions for Java. It is assumed that FindJava.cmake +# has already been loaded. See FindJava.cmake for information on how to +# load Java into your CMake project. +# +# add_jar(TARGET_NAME SRC1 SRC2 .. SRCN RCS1 RCS2 .. RCSN) +# +# This command creates a <TARGET_NAME>.jar. It compiles the given source +# files (SRC) and adds the given resource files (RCS) to the jar file. +# If only resource files are given then just a jar file is created. +# +# Additional instructions: +# To add compile flags to the target you can set these flags with +# the following variable: +# +# set(CMAKE_JAVA_COMPILE_FLAGS -nowarn) +# +# To add a path or a jar file to the class path you can do this +# with the CMAKE_JAVA_INCLUDE_PATH variable. +# +# set(CMAKE_JAVA_INCLUDE_PATH /usr/share/java/shibboleet.jar) +# +# To use a different output name for the target you can set it with: +# +# set(CMAKE_JAVA_TARGET_OUTPUT_NAME shibboleet.jar) +# add_jar(foobar foobar.java) +# +# To use a different output directory than CMAKE_CURRENT_BINARY_DIR +# you can set it with: +# +# set(CMAKE_JAVA_TARGET_OUTPUT_DIR ${PROJECT_BINARY_DIR}/bin) +# +# To define an entry point in your jar you can set it with: +# +# set(CMAKE_JAVA_JAR_ENTRY_POINT com/examples/MyProject/Main) +# +# To add a VERSION to the target output name you can set it using +# CMAKE_JAVA_TARGET_VERSION. This will create a jar file with the name +# shibboleet-1.0.0.jar and will create a symlink shibboleet.jar +# pointing to the jar with the version information. +# +# set(CMAKE_JAVA_TARGET_VERSION 1.2.0) +# add_jar(shibboleet shibbotleet.java) +# +# If the target is a JNI library, utilize the following commands to +# create a JNI symbolic link: +# +# set(CMAKE_JNI_TARGET TRUE) +# set(CMAKE_JAVA_TARGET_VERSION 1.2.0) +# add_jar(shibboleet shibbotleet.java) +# install_jar(shibboleet ${LIB_INSTALL_DIR}/shibboleet) +# install_jni_symlink(shibboleet ${JAVA_LIB_INSTALL_DIR}) +# +# If a single target needs to produce more than one jar from its +# java source code, to prevent the accumulation of duplicate class +# files in subsequent jars, set/reset CMAKE_JAR_CLASSES_PREFIX prior +# to calling the add_jar() function: +# +# set(CMAKE_JAR_CLASSES_PREFIX com/redhat/foo) +# add_jar(foo foo.java) +# +# set(CMAKE_JAR_CLASSES_PREFIX com/redhat/bar) +# add_jar(bar bar.java) +# +# Target Properties: +# The add_jar() functions sets some target properties. You can get these +# properties with the +# get_property(TARGET <target_name> PROPERTY <propery_name>) +# command. +# +# INSTALL_FILES The files which should be installed. This is used by +# install_jar(). +# JNI_SYMLINK The JNI symlink which should be installed. +# This is used by install_jni_symlink(). +# JAR_FILE The location of the jar file so that you can include +# it. +# CLASS_DIR The directory where the class files can be found. For +# example to use them with javah. +# +# find_jar(<VAR> +# name | NAMES name1 [name2 ...] +# [PATHS path1 [path2 ... ENV var]] +# [VERSIONS version1 [version2]] +# [DOC "cache documentation string"] +# ) +# +# This command is used to find a full path to the named jar. A cache +# entry named by <VAR> is created to stor the result of this command. If +# the full path to a jar is found the result is stored in the variable +# and the search will not repeated unless the variable is cleared. If +# nothing is found, the result will be <VAR>-NOTFOUND, and the search +# will be attempted again next time find_jar is invoked with the same +# variable. +# The name of the full path to a file that is searched for is specified +# by the names listed after NAMES argument. Additional search locations +# can be specified after the PATHS argument. If you require special a +# version of a jar file you can specify it with the VERSIONS argument. +# The argument after DOC will be used for the documentation string in +# the cache. +# +# install_jar(TARGET_NAME DESTINATION) +# +# This command installs the TARGET_NAME files to the given DESTINATION. +# It should be called in the same scope as add_jar() or it will fail. +# +# install_jni_symlink(TARGET_NAME DESTINATION) +# +# This command installs the TARGET_NAME JNI symlinks to the given +# DESTINATION. It should be called in the same scope as add_jar() +# or it will fail. +# +# create_javadoc(<VAR> +# PACKAGES pkg1 [pkg2 ...] +# [SOURCEPATH <sourcepath>] +# [CLASSPATH <classpath>] +# [INSTALLPATH <install path>] +# [DOCTITLE "the documentation title"] +# [WINDOWTITLE "the title of the document"] +# [AUTHOR TRUE|FALSE] +# [USE TRUE|FALSE] +# [VERSION TRUE|FALSE] +# ) +# +# Create java documentation based on files or packages. For more +# details please read the javadoc manpage. +# +# There are two main signatures for create_javadoc. The first +# signature works with package names on a path with source files: +# +# Example: +# create_javadoc(my_example_doc +# PACKAGES com.exmaple.foo com.example.bar +# SOURCEPATH "${CMAKE_CURRENT_SOURCE_DIR}" +# CLASSPATH ${CMAKE_JAVA_INCLUDE_PATH} +# WINDOWTITLE "My example" +# DOCTITLE "<h1>My example</h1>" +# AUTHOR TRUE +# USE TRUE +# VERSION TRUE +# ) +# +# The second signature for create_javadoc works on a given list of +# files. +# +# create_javadoc(<VAR> +# FILES file1 [file2 ...] +# [CLASSPATH <classpath>] +# [INSTALLPATH <install path>] +# [DOCTITLE "the documentation title"] +# [WINDOWTITLE "the title of the document"] +# [AUTHOR TRUE|FALSE] +# [USE TRUE|FALSE] +# [VERSION TRUE|FALSE] +# ) +# +# Example: +# create_javadoc(my_example_doc +# FILES ${example_SRCS} +# CLASSPATH ${CMAKE_JAVA_INCLUDE_PATH} +# WINDOWTITLE "My example" +# DOCTITLE "<h1>My example</h1>" +# AUTHOR TRUE +# USE TRUE +# VERSION TRUE +# ) +# +# Both signatures share most of the options. These options are the +# same as what you can find in the javadoc manpage. Please look at +# the manpage for CLASSPATH, DOCTITLE, WINDOWTITLE, AUTHOR, USE and +# VERSION. +# +# The documentation will be by default installed to +# +# ${CMAKE_INSTALL_PREFIX}/share/javadoc/<VAR> +# +# if you don't set the INSTALLPATH. +# + +#============================================================================= +# Copyright 2010-2011 Andreas schneider <asn@redhat.com> +# Copyright 2010 Ben Boeckel <ben.boeckel@kitware.com> +# +# Distributed under the OSI-approved BSD License (the "License"); +# see accompanying file Copyright.txt for details. +# +# This software is distributed WITHOUT ANY WARRANTY; without even the +# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. +# See the License for more information. +#============================================================================= +# (To distribute this file outside of CMake, substitute the full +# License text for the above reference.) + +function (__java_copy_file src dest comment) + add_custom_command( + OUTPUT ${dest} + COMMAND cmake -E copy_if_different + ARGS ${src} + ${dest} + DEPENDS ${src} + COMMENT ${comment}) +endfunction (__java_copy_file src dest comment) + +# define helper scripts +set(_JAVA_CLASS_FILELIST_SCRIPT ${CMAKE_CURRENT_LIST_DIR}/UseJavaClassFilelist.cmake) +set(_JAVA_SYMLINK_SCRIPT ${CMAKE_CURRENT_LIST_DIR}/UseJavaSymlinks.cmake) + +function(add_jar _TARGET_NAME) + set(_JAVA_SOURCE_FILES ${ARGN}) + + if (NOT DEFINED CMAKE_JAVA_TARGET_OUTPUT_DIR) + set(CMAKE_JAVA_TARGET_OUTPUT_DIR ${CMAKE_CURRENT_BINARY_DIR}) + endif(NOT DEFINED CMAKE_JAVA_TARGET_OUTPUT_DIR) + + if (CMAKE_JAVA_JAR_ENTRY_POINT) + set(_ENTRY_POINT_OPTION e) + set(_ENTRY_POINT_VALUE ${CMAKE_JAVA_JAR_ENTRY_POINT}) + endif (CMAKE_JAVA_JAR_ENTRY_POINT) + + if (LIBRARY_OUTPUT_PATH) + set(CMAKE_JAVA_LIBRARY_OUTPUT_PATH ${LIBRARY_OUTPUT_PATH}) + else (LIBRARY_OUTPUT_PATH) + set(CMAKE_JAVA_LIBRARY_OUTPUT_PATH ${CMAKE_JAVA_TARGET_OUTPUT_DIR}) + endif (LIBRARY_OUTPUT_PATH) + + set(CMAKE_JAVA_INCLUDE_PATH + ${CMAKE_JAVA_INCLUDE_PATH} + ${CMAKE_CURRENT_SOURCE_DIR} + ${CMAKE_JAVA_OBJECT_OUTPUT_PATH} + ${CMAKE_JAVA_LIBRARY_OUTPUT_PATH} + ) + + if (WIN32 AND NOT CYGWIN AND NOT CMAKE_CROSSCOMPILING) + set(CMAKE_JAVA_INCLUDE_FLAG_SEP ";") + else () + set(CMAKE_JAVA_INCLUDE_FLAG_SEP ":") + endif() + + foreach (JAVA_INCLUDE_DIR ${CMAKE_JAVA_INCLUDE_PATH}) + set(CMAKE_JAVA_INCLUDE_PATH_FINAL "${CMAKE_JAVA_INCLUDE_PATH_FINAL}${CMAKE_JAVA_INCLUDE_FLAG_SEP}${JAVA_INCLUDE_DIR}") + endforeach(JAVA_INCLUDE_DIR) + + set(CMAKE_JAVA_CLASS_OUTPUT_PATH "${CMAKE_JAVA_TARGET_OUTPUT_DIR}${CMAKE_FILES_DIRECTORY}/${_TARGET_NAME}.dir") + + set(_JAVA_TARGET_OUTPUT_NAME "${_TARGET_NAME}.jar") + if (CMAKE_JAVA_TARGET_OUTPUT_NAME AND CMAKE_JAVA_TARGET_VERSION) + set(_JAVA_TARGET_OUTPUT_NAME "${CMAKE_JAVA_TARGET_OUTPUT_NAME}-${CMAKE_JAVA_TARGET_VERSION}.jar") + set(_JAVA_TARGET_OUTPUT_LINK "${CMAKE_JAVA_TARGET_OUTPUT_NAME}.jar") + elseif (CMAKE_JAVA_TARGET_VERSION) + set(_JAVA_TARGET_OUTPUT_NAME "${_TARGET_NAME}-${CMAKE_JAVA_TARGET_VERSION}.jar") + set(_JAVA_TARGET_OUTPUT_LINK "${_TARGET_NAME}.jar") + elseif (CMAKE_JAVA_TARGET_OUTPUT_NAME) + set(_JAVA_TARGET_OUTPUT_NAME "${CMAKE_JAVA_TARGET_OUTPUT_NAME}.jar") + endif (CMAKE_JAVA_TARGET_OUTPUT_NAME AND CMAKE_JAVA_TARGET_VERSION) + # reset + set(CMAKE_JAVA_TARGET_OUTPUT_NAME) + + set(_JAVA_CLASS_FILES) + set(_JAVA_COMPILE_FILES) + set(_JAVA_DEPENDS) + set(_JAVA_RESOURCE_FILES) + foreach(_JAVA_SOURCE_FILE ${_JAVA_SOURCE_FILES}) + get_filename_component(_JAVA_EXT ${_JAVA_SOURCE_FILE} EXT) + get_filename_component(_JAVA_FILE ${_JAVA_SOURCE_FILE} NAME_WE) + get_filename_component(_JAVA_PATH ${_JAVA_SOURCE_FILE} PATH) + get_filename_component(_JAVA_FULL ${_JAVA_SOURCE_FILE} ABSOLUTE) + + file(RELATIVE_PATH _JAVA_REL_BINARY_PATH ${CMAKE_JAVA_TARGET_OUTPUT_DIR} ${_JAVA_FULL}) + file(RELATIVE_PATH _JAVA_REL_SOURCE_PATH ${CMAKE_CURRENT_SOURCE_DIR} ${_JAVA_FULL}) + string(LENGTH ${_JAVA_REL_BINARY_PATH} _BIN_LEN) + string(LENGTH ${_JAVA_REL_SOURCE_PATH} _SRC_LEN) + if (${_BIN_LEN} LESS ${_SRC_LEN}) + set(_JAVA_REL_PATH ${_JAVA_REL_BINARY_PATH}) + else (${_BIN_LEN} LESS ${_SRC_LEN}) + set(_JAVA_REL_PATH ${_JAVA_REL_SOURCE_PATH}) + endif (${_BIN_LEN} LESS ${_SRC_LEN}) + get_filename_component(_JAVA_REL_PATH ${_JAVA_REL_PATH} PATH) + + if (_JAVA_EXT MATCHES ".java") + list(APPEND _JAVA_COMPILE_FILES ${_JAVA_SOURCE_FILE}) + set(_JAVA_CLASS_FILE "${CMAKE_JAVA_CLASS_OUTPUT_PATH}/${_JAVA_REL_PATH}/${_JAVA_FILE}.class") + set(_JAVA_CLASS_FILES ${_JAVA_CLASS_FILES} ${_JAVA_CLASS_FILE}) + + elseif (_JAVA_EXT MATCHES ".jar" + OR _JAVA_EXT MATCHES ".war" + OR _JAVA_EXT MATCHES ".ear" + OR _JAVA_EXT MATCHES ".sar") + list(APPEND CMAKE_JAVA_INCLUDE_PATH ${_JAVA_SOURCE_FILE}) + + elseif (_JAVA_EXT STREQUAL "") + list(APPEND CMAKE_JAVA_INCLUDE_PATH ${JAVA_JAR_TARGET_${_JAVA_SOURCE_FILE}} ${JAVA_JAR_TARGET_${_JAVA_SOURCE_FILE}_CLASSPATH}) + list(APPEND _JAVA_DEPENDS ${JAVA_JAR_TARGET_${_JAVA_SOURCE_FILE}}) + + else (_JAVA_EXT MATCHES ".java") + __java_copy_file(${CMAKE_CURRENT_SOURCE_DIR}/${_JAVA_SOURCE_FILE} + ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/${_JAVA_SOURCE_FILE} + "Copying ${_JAVA_SOURCE_FILE} to the build directory") + list(APPEND _JAVA_RESOURCE_FILES ${_JAVA_SOURCE_FILE}) + endif (_JAVA_EXT MATCHES ".java") + endforeach(_JAVA_SOURCE_FILE) + + # create an empty java_class_filelist + if (NOT EXISTS ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_class_filelist) + file(WRITE ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_class_filelist "") + endif() + + if (_JAVA_COMPILE_FILES) + # Compile the java files and create a list of class files + add_custom_command( + # NOTE: this command generates an artificial dependency file + OUTPUT ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_compiled_${_TARGET_NAME} + COMMAND ${Java_JAVAC_EXECUTABLE} + ${CMAKE_JAVA_COMPILE_FLAGS} + -classpath "${CMAKE_JAVA_INCLUDE_PATH_FINAL}" + -d ${CMAKE_JAVA_CLASS_OUTPUT_PATH} + ${_JAVA_COMPILE_FILES} + COMMAND ${CMAKE_COMMAND} -E touch ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_compiled_${_TARGET_NAME} + DEPENDS ${_JAVA_COMPILE_FILES} + WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} + COMMENT "Building Java objects for ${_TARGET_NAME}.jar" + ) + add_custom_command( + OUTPUT ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_class_filelist + COMMAND ${CMAKE_COMMAND} + -DCMAKE_JAVA_CLASS_OUTPUT_PATH=${CMAKE_JAVA_CLASS_OUTPUT_PATH} + -DCMAKE_JAR_CLASSES_PREFIX="${CMAKE_JAR_CLASSES_PREFIX}" + -P ${_JAVA_CLASS_FILELIST_SCRIPT} + DEPENDS ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_compiled_${_TARGET_NAME} + WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} + ) + endif (_JAVA_COMPILE_FILES) + + # create the jar file + set(_JAVA_JAR_OUTPUT_PATH + ${CMAKE_JAVA_TARGET_OUTPUT_DIR}/${_JAVA_TARGET_OUTPUT_NAME}) + if (CMAKE_JNI_TARGET) + add_custom_command( + OUTPUT ${_JAVA_JAR_OUTPUT_PATH} + COMMAND ${Java_JAR_EXECUTABLE} + -cf${_ENTRY_POINT_OPTION} ${_JAVA_JAR_OUTPUT_PATH} ${_ENTRY_POINT_VALUE} + ${_JAVA_RESOURCE_FILES} @java_class_filelist + COMMAND ${CMAKE_COMMAND} + -D_JAVA_TARGET_DIR=${CMAKE_JAVA_TARGET_OUTPUT_DIR} + -D_JAVA_TARGET_OUTPUT_NAME=${_JAVA_TARGET_OUTPUT_NAME} + -D_JAVA_TARGET_OUTPUT_LINK=${_JAVA_TARGET_OUTPUT_LINK} + -P ${_JAVA_SYMLINK_SCRIPT} + COMMAND ${CMAKE_COMMAND} + -D_JAVA_TARGET_DIR=${CMAKE_JAVA_TARGET_OUTPUT_DIR} + -D_JAVA_TARGET_OUTPUT_NAME=${_JAVA_JAR_OUTPUT_PATH} + -D_JAVA_TARGET_OUTPUT_LINK=${_JAVA_TARGET_OUTPUT_LINK} + -P ${_JAVA_SYMLINK_SCRIPT} + DEPENDS ${_JAVA_RESOURCE_FILES} ${_JAVA_DEPENDS} ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_class_filelist + WORKING_DIRECTORY ${CMAKE_JAVA_CLASS_OUTPUT_PATH} + COMMENT "Creating Java archive ${_JAVA_TARGET_OUTPUT_NAME}" + ) + else () + add_custom_command( + OUTPUT ${_JAVA_JAR_OUTPUT_PATH} + COMMAND ${Java_JAR_EXECUTABLE} + -cf${_ENTRY_POINT_OPTION} ${_JAVA_JAR_OUTPUT_PATH} ${_ENTRY_POINT_VALUE} + ${_JAVA_RESOURCE_FILES} @java_class_filelist + COMMAND ${CMAKE_COMMAND} + -D_JAVA_TARGET_DIR=${CMAKE_JAVA_TARGET_OUTPUT_DIR} + -D_JAVA_TARGET_OUTPUT_NAME=${_JAVA_TARGET_OUTPUT_NAME} + -D_JAVA_TARGET_OUTPUT_LINK=${_JAVA_TARGET_OUTPUT_LINK} + -P ${_JAVA_SYMLINK_SCRIPT} + WORKING_DIRECTORY ${CMAKE_JAVA_CLASS_OUTPUT_PATH} + DEPENDS ${_JAVA_RESOURCE_FILES} ${_JAVA_DEPENDS} ${CMAKE_JAVA_CLASS_OUTPUT_PATH}/java_class_filelist + COMMENT "Creating Java archive ${_JAVA_TARGET_OUTPUT_NAME}" + ) + endif (CMAKE_JNI_TARGET) + + # Add the target and make sure we have the latest resource files. + add_custom_target(${_TARGET_NAME} ALL DEPENDS ${_JAVA_JAR_OUTPUT_PATH}) + + set_property( + TARGET + ${_TARGET_NAME} + PROPERTY + INSTALL_FILES + ${_JAVA_JAR_OUTPUT_PATH} + ) + + if (_JAVA_TARGET_OUTPUT_LINK) + set_property( + TARGET + ${_TARGET_NAME} + PROPERTY + INSTALL_FILES + ${_JAVA_JAR_OUTPUT_PATH} + ${CMAKE_JAVA_TARGET_OUTPUT_DIR}/${_JAVA_TARGET_OUTPUT_LINK} + ) + + if (CMAKE_JNI_TARGET) + set_property( + TARGET + ${_TARGET_NAME} + PROPERTY + JNI_SYMLINK + ${CMAKE_JAVA_TARGET_OUTPUT_DIR}/${_JAVA_TARGET_OUTPUT_LINK} + ) + endif (CMAKE_JNI_TARGET) + endif (_JAVA_TARGET_OUTPUT_LINK) + + set_property( + TARGET + ${_TARGET_NAME} + PROPERTY + JAR_FILE + ${_JAVA_JAR_OUTPUT_PATH} + ) + + set_property( + TARGET + ${_TARGET_NAME} + PROPERTY + CLASSDIR + ${CMAKE_JAVA_CLASS_OUTPUT_PATH} + ) + +endfunction(add_jar) + +function(INSTALL_JAR _TARGET_NAME _DESTINATION) + get_property(__FILES + TARGET + ${_TARGET_NAME} + PROPERTY + INSTALL_FILES + ) + + if (__FILES) + install( + FILES + ${__FILES} + DESTINATION + ${_DESTINATION} + ) + else (__FILES) + message(SEND_ERROR "The target ${_TARGET_NAME} is not known in this scope.") + endif (__FILES) +endfunction(INSTALL_JAR _TARGET_NAME _DESTINATION) + +function(INSTALL_JNI_SYMLINK _TARGET_NAME _DESTINATION) + get_property(__SYMLINK + TARGET + ${_TARGET_NAME} + PROPERTY + JNI_SYMLINK + ) + + if (__SYMLINK) + install( + FILES + ${__SYMLINK} + DESTINATION + ${_DESTINATION} + ) + else (__SYMLINK) + message(SEND_ERROR "The target ${_TARGET_NAME} is not known in this scope.") + endif (__SYMLINK) +endfunction(INSTALL_JNI_SYMLINK _TARGET_NAME _DESTINATION) + +function (find_jar VARIABLE) + set(_jar_names) + set(_jar_files) + set(_jar_versions) + set(_jar_paths + /usr/share/java/ + /usr/local/share/java/ + ${Java_JAR_PATHS}) + set(_jar_doc "NOTSET") + + set(_state "name") + + foreach (arg ${ARGN}) + if (${_state} STREQUAL "name") + if (${arg} STREQUAL "VERSIONS") + set(_state "versions") + elseif (${arg} STREQUAL "NAMES") + set(_state "names") + elseif (${arg} STREQUAL "PATHS") + set(_state "paths") + elseif (${arg} STREQUAL "DOC") + set(_state "doc") + else (${arg} STREQUAL "NAMES") + set(_jar_names ${arg}) + if (_jar_doc STREQUAL "NOTSET") + set(_jar_doc "Finding ${arg} jar") + endif (_jar_doc STREQUAL "NOTSET") + endif (${arg} STREQUAL "VERSIONS") + elseif (${_state} STREQUAL "versions") + if (${arg} STREQUAL "NAMES") + set(_state "names") + elseif (${arg} STREQUAL "PATHS") + set(_state "paths") + elseif (${arg} STREQUAL "DOC") + set(_state "doc") + else (${arg} STREQUAL "NAMES") + set(_jar_versions ${_jar_versions} ${arg}) + endif (${arg} STREQUAL "NAMES") + elseif (${_state} STREQUAL "names") + |
