* Formatting for many android classes which needed it desperately
* Moved JmeSystem.Platform to its own class in core. Desktop's and Android's JmeSystem now both use it * Moved proper usage of efficient data from AndroidSkyFactory to SkyFactory, deprecated AndroidSkyFactory git-svn-id: https://jmonkeyengine.googlecode.com/svn/trunk@8236 75d07b2b-3a1a-0410-a2c5-0572b91ccdca
This commit is contained in:
parent
45d1a0e772
commit
5ac90f46fa
@ -1,6 +1,7 @@
|
|||||||
package com.jme3.app;
|
package com.jme3.app;
|
||||||
|
|
||||||
import java.util.logging.Handler;
|
import java.util.logging.Handler;
|
||||||
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
import java.util.logging.SimpleFormatter;
|
import java.util.logging.SimpleFormatter;
|
||||||
import com.jme3.util.JmeFormatter;
|
import com.jme3.util.JmeFormatter;
|
||||||
@ -28,41 +29,35 @@ import com.jme3.system.JmeSystem;
|
|||||||
import com.jme3.system.android.OGLESContext;
|
import com.jme3.system.android.OGLESContext;
|
||||||
import com.jme3.system.android.AndroidConfigChooser.ConfigType;
|
import com.jme3.system.android.AndroidConfigChooser.ConfigType;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <code>AndroidHarness</code> wraps a jme application object and runs it on Android
|
* <code>AndroidHarness</code> wraps a jme application object and runs it on Android
|
||||||
* @author Kirill
|
* @author Kirill
|
||||||
* @author larynx
|
* @author larynx
|
||||||
*/
|
*/
|
||||||
public class AndroidHarness extends Activity implements TouchListener, DialogInterface.OnClickListener
|
public class AndroidHarness extends Activity implements TouchListener, DialogInterface.OnClickListener {
|
||||||
{
|
|
||||||
protected final static Logger logger = Logger.getLogger(AndroidHarness.class.getName());
|
protected final static Logger logger = Logger.getLogger(AndroidHarness.class.getName());
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The application class to start
|
* The application class to start
|
||||||
*/
|
*/
|
||||||
protected String appClass = "jme3test.android.Test";
|
protected String appClass = "jme3test.android.Test";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The jme3 application object
|
* The jme3 application object
|
||||||
*/
|
*/
|
||||||
protected Application app = null;
|
protected Application app = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ConfigType.FASTEST is RGB565, GLSurfaceView default
|
* ConfigType.FASTEST is RGB565, GLSurfaceView default
|
||||||
* ConfigType.BEST is RGBA8888 or better if supported by the hardware
|
* ConfigType.BEST is RGBA8888 or better if supported by the hardware
|
||||||
*/
|
*/
|
||||||
protected ConfigType eglConfigType = ConfigType.FASTEST;
|
protected ConfigType eglConfigType = ConfigType.FASTEST;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* If true all valid and not valid egl configs are logged
|
* If true all valid and not valid egl configs are logged
|
||||||
*/
|
*/
|
||||||
protected boolean eglConfigVerboseLogging = false;
|
protected boolean eglConfigVerboseLogging = false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* If true MouseEvents are generated from TouchEvents
|
* If true MouseEvents are generated from TouchEvents
|
||||||
*/
|
*/
|
||||||
protected boolean mouseEventsEnabled = true;
|
protected boolean mouseEventsEnabled = true;
|
||||||
/**
|
/**
|
||||||
* Flip X axis
|
* Flip X axis
|
||||||
*/
|
*/
|
||||||
@ -71,7 +66,6 @@ public class AndroidHarness extends Activity implements TouchListener, DialogInt
|
|||||||
* Flip Y axis
|
* Flip Y axis
|
||||||
*/
|
*/
|
||||||
protected boolean mouseEventsInvertY = true;
|
protected boolean mouseEventsInvertY = true;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Title of the exit dialog, default is "Do you want to exit?"
|
* Title of the exit dialog, default is "Do you want to exit?"
|
||||||
*/
|
*/
|
||||||
@ -80,7 +74,6 @@ public class AndroidHarness extends Activity implements TouchListener, DialogInt
|
|||||||
* Message of the exit dialog, default is "Use your home key to bring this app into the background or exit to terminate it."
|
* Message of the exit dialog, default is "Use your home key to bring this app into the background or exit to terminate it."
|
||||||
*/
|
*/
|
||||||
protected String exitDialogMessage = "Use your home key to bring this app into the background or exit to terminate it.";
|
protected String exitDialogMessage = "Use your home key to bring this app into the background or exit to terminate it.";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the screen orientation, default is SENSOR
|
* Set the screen orientation, default is SENSOR
|
||||||
* ActivityInfo.SCREEN_ORIENTATION_* constants
|
* ActivityInfo.SCREEN_ORIENTATION_* constants
|
||||||
@ -95,31 +88,27 @@ public class AndroidHarness extends Activity implements TouchListener, DialogInt
|
|||||||
* SCREEN_ORIENTATION_NOSENSOR
|
* SCREEN_ORIENTATION_NOSENSOR
|
||||||
*/
|
*/
|
||||||
protected int screenOrientation = ActivityInfo.SCREEN_ORIENTATION_SENSOR;
|
protected int screenOrientation = ActivityInfo.SCREEN_ORIENTATION_SENSOR;
|
||||||
|
|
||||||
protected OGLESContext ctx;
|
protected OGLESContext ctx;
|
||||||
protected GLSurfaceView view = null;
|
protected GLSurfaceView view = null;
|
||||||
protected boolean isGLThreadPaused = true;
|
protected boolean isGLThreadPaused = true;
|
||||||
final private String ESCAPE_EVENT = "TouchEscape";
|
final private String ESCAPE_EVENT = "TouchEscape";
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onCreate(Bundle savedInstanceState)
|
public void onCreate(Bundle savedInstanceState) {
|
||||||
{
|
|
||||||
super.onCreate(savedInstanceState);
|
super.onCreate(savedInstanceState);
|
||||||
|
|
||||||
Logger log = logger;
|
Logger log = logger;
|
||||||
boolean bIsLogFormatSet = false;
|
boolean bIsLogFormatSet = false;
|
||||||
do
|
do {
|
||||||
{
|
if (log.getHandlers().length == 0) {
|
||||||
if (log.getHandlers().length == 0)
|
|
||||||
{
|
|
||||||
log = logger.getParent();
|
log = logger.getParent();
|
||||||
if (log != null)
|
if (log != null) {
|
||||||
for (Handler h : log.getHandlers())
|
for (Handler h : log.getHandlers()) {
|
||||||
{
|
|
||||||
//h.setFormatter(new SimpleFormatter());
|
//h.setFormatter(new SimpleFormatter());
|
||||||
h.setFormatter(new JmeFormatter());
|
h.setFormatter(new JmeFormatter());
|
||||||
bIsLogFormatSet = true;
|
bIsLogFormatSet = true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} while (log != null && !bIsLogFormatSet);
|
} while (log != null && !bIsLogFormatSet);
|
||||||
|
|
||||||
@ -128,201 +117,172 @@ public class AndroidHarness extends Activity implements TouchListener, DialogInt
|
|||||||
|
|
||||||
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
||||||
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
|
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
|
||||||
WindowManager.LayoutParams.FLAG_FULLSCREEN);
|
WindowManager.LayoutParams.FLAG_FULLSCREEN);
|
||||||
|
|
||||||
setRequestedOrientation(screenOrientation);
|
setRequestedOrientation(screenOrientation);
|
||||||
|
|
||||||
// Create Settings
|
// Create Settings
|
||||||
AppSettings settings = new AppSettings(true);
|
AppSettings settings = new AppSettings(true);
|
||||||
|
|
||||||
// Create the input class
|
// Create the input class
|
||||||
AndroidInput input = new AndroidInput(this);
|
AndroidInput input = new AndroidInput(this);
|
||||||
input.setMouseEventsInvertX(mouseEventsInvertX);
|
input.setMouseEventsInvertX(mouseEventsInvertX);
|
||||||
input.setMouseEventsInvertY(mouseEventsInvertY);
|
input.setMouseEventsInvertY(mouseEventsInvertY);
|
||||||
input.setMouseEventsEnabled(mouseEventsEnabled);
|
input.setMouseEventsEnabled(mouseEventsEnabled);
|
||||||
|
|
||||||
// Create application instance
|
// Create application instance
|
||||||
try
|
try {
|
||||||
{
|
if (app == null) {
|
||||||
if (app == null)
|
|
||||||
{
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
Class<? extends Application> clazz = (Class<? extends Application>) Class.forName(appClass);
|
Class<? extends Application> clazz = (Class<? extends Application>) Class.forName(appClass);
|
||||||
app = clazz.newInstance();
|
app = clazz.newInstance();
|
||||||
}
|
}
|
||||||
|
|
||||||
app.setSettings(settings);
|
app.setSettings(settings);
|
||||||
app.start();
|
app.start();
|
||||||
ctx = (OGLESContext) app.getContext();
|
ctx = (OGLESContext) app.getContext();
|
||||||
view = ctx.createView(input, eglConfigType, eglConfigVerboseLogging);
|
view = ctx.createView(input, eglConfigType, eglConfigVerboseLogging);
|
||||||
setContentView(view);
|
setContentView(view);
|
||||||
|
|
||||||
// Set the screen reolution
|
// Set the screen reolution
|
||||||
WindowManager wind = this.getWindowManager();
|
WindowManager wind = this.getWindowManager();
|
||||||
Display disp = wind.getDefaultDisplay();
|
Display disp = wind.getDefaultDisplay();
|
||||||
ctx.getSettings().setResolution(disp.getWidth(), disp.getHeight());
|
ctx.getSettings().setResolution(disp.getWidth(), disp.getHeight());
|
||||||
|
|
||||||
AppSettings s = ctx.getSettings();
|
AppSettings s = ctx.getSettings();
|
||||||
logger.info("Settings: Width " + s.getWidth() + " Height " + s.getHeight());
|
logger.log(Level.INFO, "Settings: Width {0} Height {1}", new Object[]{s.getWidth(), s.getHeight()});
|
||||||
|
} catch (Exception ex) {
|
||||||
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
handleError("Class " + appClass + " init failed", ex);
|
handleError("Class " + appClass + " init failed", ex);
|
||||||
setContentView(new TextView(this));
|
setContentView(new TextView(this));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onRestart()
|
protected void onRestart() {
|
||||||
{
|
super.onRestart();
|
||||||
super.onRestart();
|
if (app != null) {
|
||||||
if (app != null)
|
|
||||||
app.restart();
|
app.restart();
|
||||||
|
}
|
||||||
logger.info("onRestart");
|
logger.info("onRestart");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onStart()
|
protected void onStart() {
|
||||||
{
|
|
||||||
super.onStart();
|
super.onStart();
|
||||||
logger.info("onStart");
|
logger.info("onStart");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onResume()
|
protected void onResume() {
|
||||||
{
|
|
||||||
super.onResume();
|
super.onResume();
|
||||||
if (view != null)
|
if (view != null) {
|
||||||
view.onResume();
|
view.onResume();
|
||||||
|
}
|
||||||
isGLThreadPaused = false;
|
isGLThreadPaused = false;
|
||||||
logger.info("onResume");
|
logger.info("onResume");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onPause()
|
protected void onPause() {
|
||||||
{
|
|
||||||
super.onPause();
|
super.onPause();
|
||||||
if (view != null)
|
if (view != null) {
|
||||||
view.onPause();
|
view.onPause();
|
||||||
|
}
|
||||||
isGLThreadPaused = true;
|
isGLThreadPaused = true;
|
||||||
logger.info("onPause");
|
logger.info("onPause");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onStop()
|
protected void onStop() {
|
||||||
{
|
|
||||||
super.onStop();
|
super.onStop();
|
||||||
logger.info("onStop");
|
logger.info("onStop");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onDestroy()
|
protected void onDestroy() {
|
||||||
{
|
if (app != null) {
|
||||||
if (app != null)
|
app.stop(!isGLThreadPaused);
|
||||||
app.stop(! isGLThreadPaused);
|
}
|
||||||
super.onDestroy();
|
super.onDestroy();
|
||||||
logger.info("onDestroy");
|
logger.info("onDestroy");
|
||||||
}
|
}
|
||||||
|
|
||||||
public Application getJmeApplication()
|
public Application getJmeApplication() {
|
||||||
{
|
|
||||||
return app;
|
return app;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Called when an error has occured. This is typically
|
* Called when an error has occured. This is typically
|
||||||
* invoked when an uncought exception is thrown in the render thread.
|
* invoked when an uncaught exception is thrown in the render thread.
|
||||||
* @param errorMsg The error message, if any, or null.
|
* @param errorMsg The error message, if any, or null.
|
||||||
* @param t Throwable object, or null.
|
* @param t Throwable object, or null.
|
||||||
*/
|
*/
|
||||||
public void handleError(final String errorMsg, final Throwable t)
|
public void handleError(final String errorMsg, final Throwable t) {
|
||||||
{
|
String sTrace = "";
|
||||||
|
if (t != null && t.getStackTrace() != null) {
|
||||||
String s = "";
|
for (StackTraceElement ste : t.getStackTrace()) {
|
||||||
if (t != null && t.getStackTrace() != null)
|
sTrace += "\tat " + ste.getClassName() + "." + ste.getMethodName() + "(";
|
||||||
{
|
if (ste.isNativeMethod()){
|
||||||
for (StackTraceElement ste: t.getStackTrace())
|
sTrace += "Native";
|
||||||
{
|
}else{
|
||||||
s += ste.getClassName() + "." + ste.getMethodName() + "(" + + ste.getLineNumber() + ") ";
|
sTrace += ste.getLineNumber();
|
||||||
|
}
|
||||||
|
sTrace += ")\n";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
final String sTrace = s;
|
final String stackTrace = sTrace;
|
||||||
|
|
||||||
logger.severe(t != null ? t.toString() : "OpenGL Exception");
|
logger.log(Level.SEVERE, t != null ? t.toString() : "OpenGL Exception");
|
||||||
logger.severe((errorMsg != null ? errorMsg + ": " : "") + sTrace);
|
logger.log(Level.SEVERE, "{0}{1}", new Object[]{errorMsg != null ? errorMsg + ": " : "", stackTrace});
|
||||||
|
|
||||||
this.runOnUiThread(new Runnable() {
|
this.runOnUiThread(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run()
|
public void run() {
|
||||||
{
|
AlertDialog dialog = new AlertDialog.Builder(AndroidHarness.this) // .setIcon(R.drawable.alert_dialog_icon)
|
||||||
AlertDialog dialog = new AlertDialog.Builder(AndroidHarness.this)
|
.setTitle(t != null ? (t.getMessage() != null ? (t.getMessage() + ": " + t.getClass().getName()) : t.getClass().getName()) : "OpenGL Exception").setPositiveButton("Kill", AndroidHarness.this).setMessage((errorMsg != null ? errorMsg + ": " : "") + stackTrace).create();
|
||||||
// .setIcon(R.drawable.alert_dialog_icon)
|
dialog.show();
|
||||||
.setTitle(t != null ? (t.getMessage() != null ? (t.getMessage() + ": " + t.getClass().getName()) : t.getClass().getName()) : "OpenGL Exception")
|
|
||||||
.setPositiveButton("Kill", AndroidHarness.this)
|
|
||||||
.setMessage((errorMsg != null ? errorMsg + ": " : "") + sTrace)
|
|
||||||
.create();
|
|
||||||
dialog.show();
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Called by the android alert dialog, terminate the activity and OpenGL rendering
|
* Called by the android alert dialog, terminate the activity and OpenGL rendering
|
||||||
* @param dialog
|
* @param dialog
|
||||||
* @param whichButton
|
* @param whichButton
|
||||||
*/
|
*/
|
||||||
public void onClick(DialogInterface dialog, int whichButton)
|
public void onClick(DialogInterface dialog, int whichButton) {
|
||||||
{
|
if (whichButton != -2) {
|
||||||
if (whichButton != -2)
|
if (app != null) {
|
||||||
{
|
|
||||||
if (app != null)
|
|
||||||
app.stop(true);
|
app.stop(true);
|
||||||
|
}
|
||||||
this.finish();
|
this.finish();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets called by the InputManager on all touch/drag/scale events
|
* Gets called by the InputManager on all touch/drag/scale events
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void onTouch(String name, TouchEvent evt, float tpf)
|
public void onTouch(String name, TouchEvent evt, float tpf) {
|
||||||
{
|
if (name.equals(ESCAPE_EVENT)) {
|
||||||
if (name.equals(ESCAPE_EVENT))
|
switch (evt.getType()) {
|
||||||
{
|
|
||||||
switch(evt.getType())
|
|
||||||
{
|
|
||||||
case KEY_UP:
|
case KEY_UP:
|
||||||
this.runOnUiThread(new Runnable()
|
this.runOnUiThread(new Runnable() {
|
||||||
{
|
|
||||||
@Override
|
@Override
|
||||||
public void run()
|
public void run() {
|
||||||
{
|
AlertDialog dialog = new AlertDialog.Builder(AndroidHarness.this) // .setIcon(R.drawable.alert_dialog_icon)
|
||||||
AlertDialog dialog = new AlertDialog.Builder(AndroidHarness.this)
|
.setTitle(exitDialogTitle).setPositiveButton("Yes", AndroidHarness.this).setNegativeButton("No", AndroidHarness.this).setMessage(exitDialogMessage).create();
|
||||||
// .setIcon(R.drawable.alert_dialog_icon)
|
dialog.show();
|
||||||
.setTitle(exitDialogTitle)
|
|
||||||
.setPositiveButton("Yes", AndroidHarness.this)
|
|
||||||
.setNegativeButton("No", AndroidHarness.this)
|
|
||||||
.setMessage(exitDialogMessage)
|
|
||||||
.create();
|
|
||||||
dialog.show();
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
break;
|
||||||
|
default:
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -29,7 +29,6 @@
|
|||||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package com.jme3.asset;
|
package com.jme3.asset;
|
||||||
|
|
||||||
import com.jme3.texture.Texture;
|
import com.jme3.texture.Texture;
|
||||||
@ -50,14 +49,14 @@ public class AndroidAssetManager extends DesktopAssetManager {
|
|||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(AndroidAssetManager.class.getName());
|
private static final Logger logger = Logger.getLogger(AndroidAssetManager.class.getName());
|
||||||
|
|
||||||
public AndroidAssetManager(){
|
public AndroidAssetManager() {
|
||||||
this(null);
|
this(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public AndroidAssetManager(boolean loadDefaults){
|
public AndroidAssetManager(boolean loadDefaults) {
|
||||||
//this(Thread.currentThread().getContextClassLoader().getResource("com/jme3/asset/Android.cfg"));
|
//this(Thread.currentThread().getContextClassLoader().getResource("com/jme3/asset/Android.cfg"));
|
||||||
this(null);
|
this(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -65,14 +64,13 @@ public class AndroidAssetManager extends DesktopAssetManager {
|
|||||||
* If URL == null then a default list of locators and loaders for android is set
|
* If URL == null then a default list of locators and loaders for android is set
|
||||||
* @param configFile
|
* @param configFile
|
||||||
*/
|
*/
|
||||||
public AndroidAssetManager(URL configFile)
|
public AndroidAssetManager(URL configFile) {
|
||||||
{
|
|
||||||
|
System.setProperty("org.xml.sax.driver", "org.xmlpull.v1.sax2.Driver");
|
||||||
System.setProperty("org.xml.sax.driver","org.xmlpull.v1.sax2.Driver");
|
|
||||||
|
|
||||||
|
// Set Default Android config
|
||||||
// Set Default Android config
|
this.registerLocator("", AndroidLocator.class);
|
||||||
this.registerLocator("", AndroidLocator.class);
|
|
||||||
this.registerLocator("", ClasspathLocator.class);
|
this.registerLocator("", ClasspathLocator.class);
|
||||||
this.registerLoader(AndroidImageLoader.class, "jpg", "bmp", "gif", "png", "jpeg");
|
this.registerLoader(AndroidImageLoader.class, "jpg", "bmp", "gif", "png", "jpeg");
|
||||||
this.registerLoader(AndroidAudioLoader.class, "ogg", "mp3");
|
this.registerLoader(AndroidAudioLoader.class, "ogg", "mp3");
|
||||||
@ -91,8 +89,8 @@ public class AndroidAssetManager extends DesktopAssetManager {
|
|||||||
this.registerLoader(com.jme3.scene.plugins.ogre.MaterialLoader.class, "material");
|
this.registerLoader(com.jme3.scene.plugins.ogre.MaterialLoader.class, "material");
|
||||||
this.registerLoader(com.jme3.scene.plugins.ogre.SceneLoader.class, "scene");
|
this.registerLoader(com.jme3.scene.plugins.ogre.SceneLoader.class, "scene");
|
||||||
this.registerLoader(com.jme3.shader.plugins.GLSLLoader.class, "vert", "frag", "glsl", "glsllib");
|
this.registerLoader(com.jme3.shader.plugins.GLSLLoader.class, "vert", "frag", "glsl", "glsllib");
|
||||||
|
|
||||||
|
|
||||||
logger.info("AndroidAssetManager created.");
|
logger.info("AndroidAssetManager created.");
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -102,18 +100,17 @@ public class AndroidAssetManager extends DesktopAssetManager {
|
|||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public Texture loadTexture(TextureKey key){
|
public Texture loadTexture(TextureKey key) {
|
||||||
Texture tex = (Texture) loadAsset(key);
|
Texture tex = (Texture) loadAsset(key);
|
||||||
|
|
||||||
// Needed for Android
|
// Needed for Android
|
||||||
tex.setMagFilter(Texture.MagFilter.Nearest);
|
tex.setMagFilter(Texture.MagFilter.Nearest);
|
||||||
tex.setAnisotropicFilter(0);
|
tex.setAnisotropicFilter(0);
|
||||||
if (tex.getMinFilter().usesMipMapLevels()){
|
if (tex.getMinFilter().usesMipMapLevels()) {
|
||||||
tex.setMinFilter(Texture.MinFilter.NearestNearestMipMap);
|
tex.setMinFilter(Texture.MinFilter.NearestNearestMipMap);
|
||||||
}else{
|
} else {
|
||||||
tex.setMinFilter(Texture.MinFilter.NearestNoMipMaps);
|
tex.setMinFilter(Texture.MinFilter.NearestNoMipMaps);
|
||||||
}
|
}
|
||||||
return tex;
|
return tex;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,6 +1,5 @@
|
|||||||
package com.jme3.system;
|
package com.jme3.system;
|
||||||
|
|
||||||
|
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
import android.content.res.Resources;
|
import android.content.res.Resources;
|
||||||
import com.jme3.util.AndroidLogHandler;
|
import com.jme3.util.AndroidLogHandler;
|
||||||
@ -24,172 +23,96 @@ import java.util.logging.Logger;
|
|||||||
|
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
|
|
||||||
|
public class JmeSystem {
|
||||||
|
|
||||||
public class JmeSystem
|
|
||||||
{
|
|
||||||
|
|
||||||
public static enum Platform {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Microsoft Windows 32 bit
|
|
||||||
*/
|
|
||||||
Windows32,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Microsoft Windows 64 bit
|
|
||||||
*/
|
|
||||||
Windows64,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Linux 32 bit
|
|
||||||
*/
|
|
||||||
Linux32,
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Linux 64 bit
|
|
||||||
*/
|
|
||||||
Linux64,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 32 bit
|
|
||||||
*/
|
|
||||||
MacOSX32,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 64 bit
|
|
||||||
*/
|
|
||||||
MacOSX64,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 32 bit PowerPC
|
|
||||||
*/
|
|
||||||
MacOSX_PPC32,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 64 bit PowerPC
|
|
||||||
*/
|
|
||||||
MacOSX_PPC64,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Android 2.2
|
|
||||||
*/
|
|
||||||
Android_Froyo,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Android 2.3
|
|
||||||
*/
|
|
||||||
Android_Gingerbread,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Android 3.0
|
|
||||||
*/
|
|
||||||
Android_Honeycomb,
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(JmeSystem.class.getName());
|
private static final Logger logger = Logger.getLogger(JmeSystem.class.getName());
|
||||||
|
|
||||||
private static boolean initialized = false;
|
private static boolean initialized = false;
|
||||||
private static boolean lowPermissions = false;
|
private static boolean lowPermissions = false;
|
||||||
private static Resources res;
|
private static Resources res;
|
||||||
private static Activity activity;
|
private static Activity activity;
|
||||||
|
|
||||||
public static void initialize(AppSettings settings)
|
public static void initialize(AppSettings settings) {
|
||||||
{
|
if (initialized) {
|
||||||
|
|
||||||
if (initialized)
|
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
initialized = true;
|
initialized = true;
|
||||||
try
|
try {
|
||||||
{
|
|
||||||
JmeFormatter formatter = new JmeFormatter();
|
JmeFormatter formatter = new JmeFormatter();
|
||||||
|
|
||||||
Handler consoleHandler = new AndroidLogHandler();
|
Handler consoleHandler = new AndroidLogHandler();
|
||||||
consoleHandler.setFormatter(formatter);
|
consoleHandler.setFormatter(formatter);
|
||||||
}
|
} catch (SecurityException ex) {
|
||||||
catch (SecurityException ex)
|
|
||||||
{
|
|
||||||
logger.log(Level.SEVERE, "Security error in creating log file", ex);
|
logger.log(Level.SEVERE, "Security error in creating log file", ex);
|
||||||
}
|
}
|
||||||
logger.info("Running on "+getFullName());
|
logger.log(Level.INFO, "Running on {0}", getFullName());
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String getFullName()
|
public static String getFullName() {
|
||||||
{
|
return "jMonkeyEngine 3.0.0 Beta (Android)";
|
||||||
return "jMonkey Engine 3 ALPHA 0.7 Android";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void setLowPermissions(boolean lowPerm)
|
public static void setLowPermissions(boolean lowPerm) {
|
||||||
{
|
|
||||||
lowPermissions = lowPerm;
|
lowPermissions = lowPerm;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean isLowPermissions()
|
public static boolean isLowPermissions() {
|
||||||
{
|
|
||||||
return lowPermissions;
|
return lowPermissions;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static JmeContext newContext(AppSettings settings, Type contextType)
|
public static JmeContext newContext(AppSettings settings, Type contextType) {
|
||||||
{
|
|
||||||
initialize(settings);
|
initialize(settings);
|
||||||
return new OGLESContext();
|
return new OGLESContext();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static AudioRenderer newAudioRenderer(AppSettings settings)
|
public static AudioRenderer newAudioRenderer(AppSettings settings) {
|
||||||
{
|
return new AndroidAudioRenderer(activity);
|
||||||
return new AndroidAudioRenderer(activity);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void setResources(Resources res)
|
public static void setResources(Resources res) {
|
||||||
{
|
|
||||||
JmeSystem.res = res;
|
JmeSystem.res = res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Resources getResources()
|
public static Resources getResources() {
|
||||||
{
|
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void setActivity(Activity activity)
|
public static void setActivity(Activity activity) {
|
||||||
{
|
|
||||||
JmeSystem.activity = activity;
|
JmeSystem.activity = activity;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Activity getActivity()
|
public static Activity getActivity() {
|
||||||
{
|
|
||||||
return activity;
|
return activity;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public static AssetManager newAssetManager()
|
public static AssetManager newAssetManager() {
|
||||||
{
|
logger.log(Level.INFO, "newAssetManager()");
|
||||||
logger.info("newAssetManager()");
|
|
||||||
return new AndroidAssetManager(null);
|
return new AndroidAssetManager(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static AssetManager newAssetManager(URL url)
|
public static AssetManager newAssetManager(URL url) {
|
||||||
{
|
logger.log(Level.INFO, "newAssetManager({0})", url);
|
||||||
logger.info("newAssetManager(" + url + ")");
|
|
||||||
return new AndroidAssetManager(url);
|
return new AndroidAssetManager(url);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean showSettingsDialog(AppSettings settings, boolean loadSettings)
|
public static boolean showSettingsDialog(AppSettings settings, boolean loadSettings) {
|
||||||
{
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Platform getPlatform()
|
public static Platform getPlatform() {
|
||||||
{
|
|
||||||
String os = System.getProperty("os.name").toLowerCase();
|
|
||||||
String arch = System.getProperty("os.arch").toLowerCase();
|
String arch = System.getProperty("os.arch").toLowerCase();
|
||||||
|
if (arch.contains("arm")){
|
||||||
return Platform.Android_Froyo;
|
if (arch.contains("v5")){
|
||||||
// throw new UnsupportedOperationException("The specified platform: "+os+" is not supported.");
|
return Platform.Android_ARM5;
|
||||||
|
}else if (arch.contains("v6")){
|
||||||
|
return Platform.Android_ARM6;
|
||||||
|
}else if (arch.contains("v7")){
|
||||||
|
return Platform.Android_ARM7;
|
||||||
|
}else{
|
||||||
|
return Platform.Android_ARM5; // unknown ARM
|
||||||
|
}
|
||||||
|
}else{
|
||||||
|
throw new UnsupportedOperationException("Unsupported Android Platform");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -14,37 +14,35 @@ import java.io.IOException;
|
|||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
public class AndroidImageLoader implements AssetLoader
|
public class AndroidImageLoader implements AssetLoader {
|
||||||
{
|
|
||||||
|
|
||||||
public Object load2(AssetInfo info) throws IOException
|
public Object load2(AssetInfo info) throws IOException {
|
||||||
{
|
|
||||||
ByteBuffer bb = BufferUtils.createByteBuffer(1 * 1 * 2);
|
ByteBuffer bb = BufferUtils.createByteBuffer(1 * 1 * 2);
|
||||||
bb.put( (byte) 0xff ).put( (byte) 0xff );
|
bb.put((byte) 0xff).put((byte) 0xff);
|
||||||
bb.clear();
|
bb.clear();
|
||||||
return new Image(Format.RGB5A1, 1, 1, bb);
|
return new Image(Format.RGB5A1, 1, 1, bb);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Object load(AssetInfo info) throws IOException
|
public Object load(AssetInfo info) throws IOException {
|
||||||
{
|
|
||||||
InputStream in = null;
|
InputStream in = null;
|
||||||
Bitmap bitmap = null;
|
Bitmap bitmap = null;
|
||||||
try {
|
try {
|
||||||
in = info.openStream();
|
in = info.openStream();
|
||||||
bitmap = BitmapFactory.decodeStream(in);
|
bitmap = BitmapFactory.decodeStream(in);
|
||||||
if (bitmap == null){
|
if (bitmap == null) {
|
||||||
throw new IOException("Failed to load image: "+info.getKey().getName());
|
throw new IOException("Failed to load image: " + info.getKey().getName());
|
||||||
}
|
}
|
||||||
} finally {
|
} finally {
|
||||||
if (in != null)
|
if (in != null) {
|
||||||
in.close();
|
in.close();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int width = bitmap.getWidth();
|
int width = bitmap.getWidth();
|
||||||
int height = bitmap.getHeight();
|
int height = bitmap.getHeight();
|
||||||
Format fmt;
|
Format fmt;
|
||||||
|
|
||||||
switch (bitmap.getConfig()){
|
switch (bitmap.getConfig()) {
|
||||||
case ALPHA_8:
|
case ALPHA_8:
|
||||||
fmt = Format.Alpha8;
|
fmt = Format.Alpha8;
|
||||||
break;
|
break;
|
||||||
@ -54,15 +52,14 @@ public class AndroidImageLoader implements AssetLoader
|
|||||||
case ARGB_8888:
|
case ARGB_8888:
|
||||||
fmt = Format.RGBA8;
|
fmt = Format.RGBA8;
|
||||||
break;
|
break;
|
||||||
case RGB_565:
|
case RGB_565:
|
||||||
fmt = Format.RGB565;
|
fmt = Format.RGB565;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( ((TextureKey)info.getKey()).isFlipY() )
|
if (((TextureKey) info.getKey()).isFlipY()) {
|
||||||
{
|
|
||||||
Bitmap newBitmap = null;
|
Bitmap newBitmap = null;
|
||||||
Matrix flipMat = new Matrix();
|
Matrix flipMat = new Matrix();
|
||||||
flipMat.preScale(1.0f, -1.0f);
|
flipMat.preScale(1.0f, -1.0f);
|
||||||
@ -70,14 +67,13 @@ public class AndroidImageLoader implements AssetLoader
|
|||||||
bitmap.recycle();
|
bitmap.recycle();
|
||||||
bitmap = newBitmap;
|
bitmap = newBitmap;
|
||||||
|
|
||||||
if (bitmap == null){
|
if (bitmap == null) {
|
||||||
throw new IOException("Failed to flip image: "+info.getKey().getName());
|
throw new IOException("Failed to flip image: " + info.getKey().getName());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Image image = new Image(fmt, width, height, null);
|
Image image = new Image(fmt, width, height, null);
|
||||||
image.setEfficentData(bitmap);
|
image.setEfficentData(bitmap);
|
||||||
return image;
|
return image;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -8,33 +8,39 @@ import java.util.NoSuchElementException;
|
|||||||
*/
|
*/
|
||||||
// suppress unchecked warnings in Java 1.5.0_6 and later
|
// suppress unchecked warnings in Java 1.5.0_6 and later
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public class RingBuffer<Item> implements Iterable<Item>
|
public class RingBuffer<Item> implements Iterable<Item> {
|
||||||
{
|
|
||||||
private Item[] buffer; // queue elements
|
private Item[] buffer; // queue elements
|
||||||
private int count = 0; // number of elements on queue
|
private int count = 0; // number of elements on queue
|
||||||
private int indexOut = 0; // index of first element of queue
|
private int indexOut = 0; // index of first element of queue
|
||||||
private int indexIn = 0; // index of next available slot
|
private int indexIn = 0; // index of next available slot
|
||||||
|
|
||||||
// cast needed since no generic array creation in Java
|
// cast needed since no generic array creation in Java
|
||||||
public RingBuffer(int capacity)
|
public RingBuffer(int capacity) {
|
||||||
{
|
|
||||||
buffer = (Item[]) new Object[capacity];
|
buffer = (Item[]) new Object[capacity];
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isEmpty() { return count == 0; }
|
public boolean isEmpty() {
|
||||||
public int size() { return count; }
|
return count == 0;
|
||||||
|
}
|
||||||
|
|
||||||
public void push(Item item)
|
public int size() {
|
||||||
{
|
return count;
|
||||||
if (count == buffer.length) { throw new RuntimeException("Ring buffer overflow"); }
|
}
|
||||||
|
|
||||||
|
public void push(Item item) {
|
||||||
|
if (count == buffer.length) {
|
||||||
|
throw new RuntimeException("Ring buffer overflow");
|
||||||
|
}
|
||||||
buffer[indexIn] = item;
|
buffer[indexIn] = item;
|
||||||
indexIn = (indexIn + 1) % buffer.length; // wrap-around
|
indexIn = (indexIn + 1) % buffer.length; // wrap-around
|
||||||
count++;
|
count++;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Item pop()
|
public Item pop() {
|
||||||
{
|
if (isEmpty()) {
|
||||||
if (isEmpty()) { throw new RuntimeException("Ring buffer underflow"); }
|
throw new RuntimeException("Ring buffer underflow");
|
||||||
|
}
|
||||||
Item item = buffer[indexOut];
|
Item item = buffer[indexOut];
|
||||||
buffer[indexOut] = null; // to help with garbage collection
|
buffer[indexOut] = null; // to help with garbage collection
|
||||||
count--;
|
count--;
|
||||||
@ -42,22 +48,28 @@ public class RingBuffer<Item> implements Iterable<Item>
|
|||||||
return item;
|
return item;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Iterator<Item> iterator() { return new RingBufferIterator(); }
|
public Iterator<Item> iterator() {
|
||||||
|
return new RingBufferIterator();
|
||||||
|
}
|
||||||
|
|
||||||
// an iterator, doesn't implement remove() since it's optional
|
// an iterator, doesn't implement remove() since it's optional
|
||||||
private class RingBufferIterator implements Iterator<Item> {
|
private class RingBufferIterator implements Iterator<Item> {
|
||||||
|
|
||||||
private int i = 0;
|
private int i = 0;
|
||||||
public boolean hasNext() { return i < count; }
|
|
||||||
public void remove() { throw new UnsupportedOperationException(); }
|
public boolean hasNext() {
|
||||||
|
return i < count;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void remove() {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
|
||||||
public Item next() {
|
public Item next() {
|
||||||
if (!hasNext()) throw new NoSuchElementException();
|
if (!hasNext()) {
|
||||||
|
throw new NoSuchElementException();
|
||||||
|
}
|
||||||
return buffer[i++];
|
return buffer[i++];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -1,148 +1,39 @@
|
|||||||
package com.jme3.util.android;
|
package com.jme3.util.android;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import android.graphics.Bitmap;
|
|
||||||
|
|
||||||
import com.jme3.asset.AssetManager;
|
import com.jme3.asset.AssetManager;
|
||||||
import com.jme3.asset.TextureKey;
|
|
||||||
import com.jme3.material.Material;
|
|
||||||
import com.jme3.math.Vector3f;
|
import com.jme3.math.Vector3f;
|
||||||
import com.jme3.renderer.queue.RenderQueue.Bucket;
|
|
||||||
import com.jme3.scene.Geometry;
|
|
||||||
import com.jme3.scene.Spatial;
|
import com.jme3.scene.Spatial;
|
||||||
import com.jme3.scene.shape.Sphere;
|
|
||||||
import com.jme3.texture.Image;
|
|
||||||
import com.jme3.texture.Image.Format;
|
|
||||||
import com.jme3.texture.Texture;
|
import com.jme3.texture.Texture;
|
||||||
import com.jme3.texture.TextureCubeMap;
|
import com.jme3.util.SkyFactory;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <code>AndroidSkyFactory</code> creates a sky box spatial
|
* <code>AndroidSkyFactory</code> creates a sky box spatial
|
||||||
* @author larynx, derived from SkyFactory and adapted for android
|
* @author larynx, derived from SkyFactory and adapted for android
|
||||||
*
|
* @deprecated Use {@link SkyFactory} instead
|
||||||
*/
|
*/
|
||||||
public class AndroidSkyFactory
|
@Deprecated
|
||||||
{
|
public class AndroidSkyFactory {
|
||||||
private static final Sphere sphereMesh = new Sphere(10, 10, 101f, false, true);
|
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture texture, Vector3f normalScale, boolean sphereMap)
|
public static Spatial createSky(AssetManager assetManager, Texture texture, Vector3f normalScale, boolean sphereMap) {
|
||||||
{
|
return SkyFactory.createSky(assetManager, texture, normalScale, sphereMap);
|
||||||
Geometry sky = new Geometry("Sky", sphereMesh);
|
|
||||||
sky.setQueueBucket(Bucket.Sky);
|
|
||||||
sky.setCullHint(Spatial.CullHint.Never);
|
|
||||||
|
|
||||||
Material skyMat = new Material(assetManager, "Common/MatDefs/Misc/Sky.j3md");
|
|
||||||
skyMat.setVector3("NormalScale", normalScale);
|
|
||||||
if (sphereMap)
|
|
||||||
{
|
|
||||||
skyMat.setBoolean("SphereMap", sphereMap);
|
|
||||||
}
|
|
||||||
else if (!(texture instanceof TextureCubeMap))
|
|
||||||
{
|
|
||||||
// make sure its a cubemap
|
|
||||||
Image img = texture.getImage();
|
|
||||||
texture = new TextureCubeMap();
|
|
||||||
texture.setImage(img);
|
|
||||||
}
|
|
||||||
skyMat.setTexture("Texture", texture);
|
|
||||||
sky.setMaterial(skyMat);
|
|
||||||
|
|
||||||
return sky;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void checkImage(Image image)
|
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south,
|
||||||
{
|
Texture up, Texture down, Vector3f normalScale) {
|
||||||
if (image.getWidth() != image.getHeight())
|
return SkyFactory.createSky(assetManager, west, east, north, south, up, down, normalScale);
|
||||||
throw new IllegalArgumentException("Image width and height must be the same");
|
|
||||||
|
|
||||||
if (image.getMultiSamples() != 1)
|
|
||||||
throw new IllegalArgumentException("Multisample textures not allowed");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void checkImagesForCubeMap(Image ... images)
|
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south,
|
||||||
{
|
Texture up, Texture down) {
|
||||||
if (images.length == 1) return;
|
return SkyFactory.createSky(assetManager, west, east, north, south, up, down, Vector3f.UNIT_XYZ);
|
||||||
|
|
||||||
Format fmt = images[0].getFormat();
|
|
||||||
int width = images[0].getWidth();
|
|
||||||
int height = images[0].getHeight();
|
|
||||||
|
|
||||||
checkImage(images[0]);
|
|
||||||
|
|
||||||
for (int i = 1; i < images.length; i++)
|
|
||||||
{
|
|
||||||
Image image = images[i];
|
|
||||||
checkImage(images[i]);
|
|
||||||
if (image.getFormat() != fmt) throw new IllegalArgumentException("Images must have same format");
|
|
||||||
if (image.getWidth() != width) throw new IllegalArgumentException("Images must have same width");
|
|
||||||
if (image.getHeight() != height) throw new IllegalArgumentException("Images must have same height");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south,
|
public static Spatial createSky(AssetManager assetManager, Texture texture, boolean sphereMap) {
|
||||||
Texture up, Texture down, Vector3f normalScale)
|
return SkyFactory.createSky(assetManager, texture, Vector3f.UNIT_XYZ, sphereMap);
|
||||||
{
|
|
||||||
Geometry sky = new Geometry("Sky", sphereMesh);
|
|
||||||
sky.setQueueBucket(Bucket.Sky);
|
|
||||||
sky.setCullHint(Spatial.CullHint.Never);
|
|
||||||
|
|
||||||
Image westImg = west.getImage();
|
|
||||||
Image eastImg = east.getImage();
|
|
||||||
Image northImg = north.getImage();
|
|
||||||
Image southImg = south.getImage();
|
|
||||||
Image upImg = up.getImage();
|
|
||||||
Image downImg = down.getImage();
|
|
||||||
|
|
||||||
checkImagesForCubeMap(westImg, eastImg, northImg, southImg, upImg, downImg);
|
|
||||||
|
|
||||||
Image cubeImage = new Image(westImg.getFormat(), westImg.getWidth(), westImg.getHeight(), null);
|
|
||||||
|
|
||||||
ArrayList<Bitmap> arrayList = new ArrayList<Bitmap>(6);
|
|
||||||
|
|
||||||
arrayList.add((Bitmap)westImg.getEfficentData());
|
|
||||||
arrayList.add((Bitmap)eastImg.getEfficentData());
|
|
||||||
|
|
||||||
arrayList.add((Bitmap)downImg.getEfficentData());
|
|
||||||
arrayList.add((Bitmap)upImg.getEfficentData());
|
|
||||||
|
|
||||||
arrayList.add((Bitmap)southImg.getEfficentData());
|
|
||||||
arrayList.add((Bitmap)northImg.getEfficentData());
|
|
||||||
|
|
||||||
cubeImage.setEfficentData(arrayList);
|
|
||||||
|
|
||||||
TextureCubeMap cubeMap = new TextureCubeMap(cubeImage);
|
|
||||||
cubeMap.setAnisotropicFilter(0);
|
|
||||||
cubeMap.setMagFilter(Texture.MagFilter.Bilinear);
|
|
||||||
cubeMap.setMinFilter(Texture.MinFilter.BilinearNoMipMaps);
|
|
||||||
cubeMap.setWrap(Texture.WrapMode.EdgeClamp);
|
|
||||||
|
|
||||||
|
|
||||||
Material skyMat = new Material(assetManager, "Common/MatDefs/Misc/Sky.j3md");
|
|
||||||
skyMat.setTexture("Texture", cubeMap);
|
|
||||||
skyMat.setVector3("NormalScale", normalScale);
|
|
||||||
sky.setMaterial(skyMat);
|
|
||||||
|
|
||||||
return sky;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south,
|
public static Spatial createSky(AssetManager assetManager, String textureName, boolean sphereMap) {
|
||||||
Texture up, Texture down)
|
return SkyFactory.createSky(assetManager, textureName, sphereMap);
|
||||||
{
|
|
||||||
return createSky(assetManager, west, east, north, south, up, down, Vector3f.UNIT_XYZ);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture texture, boolean sphereMap)
|
|
||||||
{
|
|
||||||
return createSky(assetManager, texture, Vector3f.UNIT_XYZ, sphereMap);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, String textureName, boolean sphereMap)
|
|
||||||
{
|
|
||||||
TextureKey key = new TextureKey(textureName, true);
|
|
||||||
key.setGenerateMips(true);
|
|
||||||
key.setAsCube(!sphereMap);
|
|
||||||
Texture tex = assetManager.loadTexture(key);
|
|
||||||
return createSky(assetManager, tex, sphereMap);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1,6 +1,5 @@
|
|||||||
package jme3test.android;
|
package jme3test.android;
|
||||||
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
@ -30,43 +29,37 @@ import jme3test.android.AndroidActivity;
|
|||||||
|
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
|
|
||||||
|
|
||||||
public class AboutActivity extends Activity {
|
public class AboutActivity extends Activity {
|
||||||
|
|
||||||
private static final java.util.logging.Logger logger = java.util.logging.Logger.getLogger(AboutActivity.class.getName());
|
private static final java.util.logging.Logger logger = java.util.logging.Logger.getLogger(AboutActivity.class.getName());
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onCreate(Bundle savedInstanceState) {
|
||||||
|
logger.info("onCreate(" + savedInstanceState + ")");
|
||||||
|
|
||||||
@Override
|
super.onCreate(savedInstanceState);
|
||||||
public void onCreate(Bundle savedInstanceState) {
|
|
||||||
logger.info("onCreate(" + savedInstanceState + ")");
|
|
||||||
|
|
||||||
super.onCreate(savedInstanceState);
|
//setContentView(R.layout.about);
|
||||||
|
}
|
||||||
|
|
||||||
//setContentView(R.layout.about);
|
@Override
|
||||||
}
|
public void onDestroy() {
|
||||||
|
logger.info("onDestroy()");
|
||||||
|
super.onDestroy();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onDestroy() {
|
protected void onResume() {
|
||||||
logger.info("onDestroy()");
|
super.onResume();
|
||||||
super.onDestroy();
|
}
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onResume() {
|
|
||||||
super.onResume();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onStart() {
|
|
||||||
super.onStart();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onStop() {
|
|
||||||
super.onStop();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onStart() {
|
||||||
|
super.onStart();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onStop() {
|
||||||
|
super.onStop();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -6,7 +6,6 @@
|
|||||||
*
|
*
|
||||||
* created: Mon Nov 8 00:08:07 EST 2010
|
* created: Mon Nov 8 00:08:07 EST 2010
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package jme3test.android;
|
package jme3test.android;
|
||||||
|
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
@ -23,136 +22,128 @@ import com.jme3.system.android.OGLESContext;
|
|||||||
import com.jme3.app.Application;
|
import com.jme3.app.Application;
|
||||||
import com.jme3.app.SimpleApplication;
|
import com.jme3.app.SimpleApplication;
|
||||||
|
|
||||||
|
|
||||||
public class AndroidActivity extends Activity {
|
public class AndroidActivity extends Activity {
|
||||||
|
|
||||||
private final static java.util.logging.Logger logger = java.util.logging.Logger.getLogger(AndroidActivity.class.getName());
|
private final static java.util.logging.Logger logger = java.util.logging.Logger.getLogger(AndroidActivity.class.getName());
|
||||||
|
private OGLESContext ctx;
|
||||||
|
private GLSurfaceView view;
|
||||||
|
private boolean useVA = false;
|
||||||
|
private boolean verboseLogging = false;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onCreate(Bundle savedInstanceState) {
|
||||||
|
|
||||||
|
super.onCreate(savedInstanceState);
|
||||||
|
|
||||||
|
JmeSystem.setResources(getResources());
|
||||||
|
|
||||||
|
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
||||||
|
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
|
||||||
|
WindowManager.LayoutParams.FLAG_FULLSCREEN);
|
||||||
|
|
||||||
|
AppSettings settings = new AppSettings(true);
|
||||||
|
|
||||||
|
String testClassName = getIntent().getStringExtra(AndroidActivity.class.getName() + ".TEST_CLASS_NAME");
|
||||||
|
|
||||||
|
logger.info("test class name: [" + testClassName + "]");
|
||||||
|
|
||||||
|
String appClass = (testClassName != null ? testClassName : "jme3test.android.SimpleTexturedTest");
|
||||||
|
|
||||||
|
useVA = getIntent().getBooleanExtra(AndroidActivity.class.getName() + ".USE_VA", false);
|
||||||
|
|
||||||
|
logger.info("USE_VA -> [" + useVA + "]");
|
||||||
|
|
||||||
|
settings.putBoolean("USE_VA", useVA);
|
||||||
|
|
||||||
|
verboseLogging = getIntent().getBooleanExtra(AndroidActivity.class.getName() + ".VERBOSE_LOGGING", false);
|
||||||
|
|
||||||
|
settings.putBoolean("VERBOSE_LOGGING", verboseLogging);
|
||||||
|
|
||||||
|
Application app = null;
|
||||||
|
|
||||||
|
try {
|
||||||
|
Class<? extends Application> clazz = (Class<? extends Application>) Class.forName(
|
||||||
|
appClass);
|
||||||
|
|
||||||
|
app = clazz.newInstance();
|
||||||
|
/*
|
||||||
|
app = (Application) java.lang.reflect.Proxy.newProxyInstance(
|
||||||
|
this.getClass().getClassLoader(),
|
||||||
|
new Class[] {Class.forName(appClass)},
|
||||||
|
|
||||||
|
new java.lang.reflect.InvocationHandler() {
|
||||||
|
public Object invoke(Object proxy, java.lang.reflect.Method method, Object[] args) throws Throwable {
|
||||||
|
if (
|
||||||
|
method.getName().equals("loadFPSText") ||
|
||||||
|
method.getName().equals("loadStatsView")
|
||||||
|
) {
|
||||||
|
logger.info("ignoring method: [" + method + "]");
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return method.invoke(proxy, args);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
);
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
private OGLESContext ctx;
|
if (app instanceof SimpleApplication) {
|
||||||
private GLSurfaceView view;
|
((SimpleApplication) app).setShowSettings(false);
|
||||||
|
}
|
||||||
|
|
||||||
private boolean useVA = false;
|
logger.info("setting settings ...");
|
||||||
private boolean verboseLogging = false;
|
app.setSettings(settings);
|
||||||
|
logger.info("setting settings ... done.");
|
||||||
|
|
||||||
@Override
|
logger.info("starting app ...");
|
||||||
public void onCreate(Bundle savedInstanceState) {
|
app.start();
|
||||||
|
logger.info("starting app ... done.");
|
||||||
|
|
||||||
super.onCreate(savedInstanceState);
|
if (app instanceof SimpleApplication) {
|
||||||
|
((SimpleApplication) app).getGuiNode().detachAllChildren();
|
||||||
|
}
|
||||||
|
|
||||||
JmeSystem.setResources(getResources());
|
logger.info("creating context ...");
|
||||||
|
ctx = (OGLESContext) app.getContext();
|
||||||
|
logger.info("creating context ... done.");
|
||||||
|
|
||||||
requestWindowFeature(Window.FEATURE_NO_TITLE);
|
ctx.setSettings(settings);
|
||||||
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
|
|
||||||
WindowManager.LayoutParams.FLAG_FULLSCREEN);
|
|
||||||
|
|
||||||
AppSettings settings = new AppSettings(true);
|
logger.info("creating view ...");
|
||||||
|
view = ctx.createView(this);
|
||||||
|
logger.info("creating view ... done.");
|
||||||
|
|
||||||
String testClassName = getIntent().getStringExtra(AndroidActivity.class.getName() + ".TEST_CLASS_NAME");
|
logger.info("setting content view ...");
|
||||||
|
setContentView(view);
|
||||||
|
logger.info("setting content done ...");
|
||||||
|
|
||||||
logger.info("test class name: [" + testClassName + "]");
|
} catch (Throwable exception) {
|
||||||
|
logger.warning("exception: " + exception);
|
||||||
|
exception.printStackTrace(System.err);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
String appClass = (testClassName != null? testClassName: "jme3test.android.SimpleTexturedTest");
|
@Override
|
||||||
|
protected void onResume() {
|
||||||
|
logger.info("onResume ...");
|
||||||
|
super.onResume();
|
||||||
|
logger.info("view.onResume ...");
|
||||||
|
|
||||||
useVA = getIntent().getBooleanExtra(AndroidActivity.class.getName() + ".USE_VA", false);
|
view.onResume();
|
||||||
|
|
||||||
logger.info("USE_VA -> [" + useVA + "]");
|
logger.info("view.onResume ... done.");
|
||||||
|
logger.info("onResume ... done.");
|
||||||
settings.putBoolean("USE_VA", useVA);
|
}
|
||||||
|
|
||||||
verboseLogging = getIntent().getBooleanExtra(AndroidActivity.class.getName() + ".VERBOSE_LOGGING", false);
|
|
||||||
|
|
||||||
settings.putBoolean("VERBOSE_LOGGING", verboseLogging);
|
|
||||||
|
|
||||||
Application app = null;
|
|
||||||
|
|
||||||
try {
|
|
||||||
Class<? extends Application> clazz = (Class<? extends Application>) Class.forName(
|
|
||||||
appClass
|
|
||||||
);
|
|
||||||
|
|
||||||
app = clazz.newInstance();
|
|
||||||
/*
|
|
||||||
app = (Application) java.lang.reflect.Proxy.newProxyInstance(
|
|
||||||
this.getClass().getClassLoader(),
|
|
||||||
new Class[] {Class.forName(appClass)},
|
|
||||||
|
|
||||||
new java.lang.reflect.InvocationHandler() {
|
|
||||||
public Object invoke(Object proxy, java.lang.reflect.Method method, Object[] args) throws Throwable {
|
|
||||||
if (
|
|
||||||
method.getName().equals("loadFPSText") ||
|
|
||||||
method.getName().equals("loadStatsView")
|
|
||||||
) {
|
|
||||||
logger.info("ignoring method: [" + method + "]");
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return method.invoke(proxy, args);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
);
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
if (app instanceof SimpleApplication) {
|
|
||||||
((SimpleApplication) app).setShowSettings(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
logger.info("setting settings ...");
|
|
||||||
app.setSettings(settings);
|
|
||||||
logger.info("setting settings ... done.");
|
|
||||||
|
|
||||||
logger.info("starting app ...");
|
|
||||||
app.start();
|
|
||||||
logger.info("starting app ... done.");
|
|
||||||
|
|
||||||
if (app instanceof SimpleApplication)
|
|
||||||
((SimpleApplication) app).getGuiNode().detachAllChildren();
|
|
||||||
|
|
||||||
logger.info("creating context ...");
|
|
||||||
ctx = (OGLESContext) app.getContext();
|
|
||||||
logger.info("creating context ... done.");
|
|
||||||
|
|
||||||
ctx.setSettings(settings);
|
|
||||||
|
|
||||||
logger.info("creating view ...");
|
|
||||||
view = ctx.createView(this);
|
|
||||||
logger.info("creating view ... done.");
|
|
||||||
|
|
||||||
logger.info("setting content view ...");
|
|
||||||
setContentView(view);
|
|
||||||
logger.info("setting content done ...");
|
|
||||||
|
|
||||||
} catch (Throwable exception) {
|
|
||||||
logger.warning("exception: " + exception);
|
|
||||||
exception.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onResume() {
|
|
||||||
logger.info("onResume ...");
|
|
||||||
super.onResume();
|
|
||||||
logger.info("view.onResume ...");
|
|
||||||
|
|
||||||
view.onResume();
|
|
||||||
|
|
||||||
logger.info("view.onResume ... done.");
|
|
||||||
logger.info("onResume ... done.");
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onPause() {
|
|
||||||
super.onPause();
|
|
||||||
view.onPause();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onPause() {
|
||||||
|
super.onPause();
|
||||||
|
view.onPause();
|
||||||
|
}
|
||||||
// @Override
|
// @Override
|
||||||
// protected void onDestroy(){
|
// protected void onDestroy(){
|
||||||
// super.onDestroy();
|
// super.onDestroy();
|
||||||
|
|
||||||
// Debug.stopMethodTracing();
|
// Debug.stopMethodTracing();
|
||||||
// }
|
// }
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -4,10 +4,8 @@
|
|||||||
*
|
*
|
||||||
* created: Mon Nov 8 00:08:22 EST 2010
|
* created: Mon Nov 8 00:08:22 EST 2010
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package jme3test.android;
|
package jme3test.android;
|
||||||
|
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
@ -35,101 +33,95 @@ import com.jme3.util.TangentBinormalGenerator;
|
|||||||
|
|
||||||
import jme3tools.converters.model.ModelConverter;
|
import jme3tools.converters.model.ModelConverter;
|
||||||
|
|
||||||
|
|
||||||
public class SimpleTexturedTest extends SimpleApplication {
|
public class SimpleTexturedTest extends SimpleApplication {
|
||||||
|
|
||||||
private static final java.util.logging.Logger logger = java.util.logging.Logger.getLogger(SimpleTexturedTest.class.getName());
|
private static final java.util.logging.Logger logger = java.util.logging.Logger.getLogger(SimpleTexturedTest.class.getName());
|
||||||
|
private Node spheresContainer = new Node("spheres-container");
|
||||||
|
private boolean lightingEnabled = true;
|
||||||
|
private boolean texturedEnabled = true;
|
||||||
|
private boolean spheres = true;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void simpleInitApp() {
|
||||||
|
|
||||||
private Node spheresContainer = new Node("spheres-container");
|
/*
|
||||||
|
* GUI rendering is broken on Android right now and prevents the main view from rendering.
|
||||||
|
* Detaching all children lets the main view to be rendered.
|
||||||
|
*/
|
||||||
|
|
||||||
|
guiNode.detachAllChildren();
|
||||||
|
|
||||||
private boolean lightingEnabled = true;
|
Mesh shape = null;
|
||||||
private boolean texturedEnabled = true;
|
|
||||||
private boolean spheres = true;
|
|
||||||
|
|
||||||
@Override
|
if (spheres) {
|
||||||
public void simpleInitApp() {
|
shape = new Sphere(16, 16, .5f);
|
||||||
|
} else {
|
||||||
|
shape = new Box(Vector3f.ZERO, 0.3f, 0.3f, 0.3f);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
// ModelConverter.optimize(geom);
|
||||||
* GUI rendering is broken on Android right now and prevents the main view from rendering.
|
|
||||||
* Detaching all children lets the main view to be rendered.
|
|
||||||
*/
|
|
||||||
|
|
||||||
guiNode.detachAllChildren();
|
Texture texture = assetManager.loadTexture(new TextureKey("icons/textured.png"));
|
||||||
|
|
||||||
Mesh shape = null;
|
Material material = null;
|
||||||
|
|
||||||
if (spheres) {
|
if (texturedEnabled) {
|
||||||
shape = new Sphere(16, 16, .5f);
|
if (lightingEnabled) {
|
||||||
} else {
|
material = new Material(assetManager, "Common/MatDefs/Light/Lighting.j3md");
|
||||||
shape = new Box(Vector3f.ZERO, 0.3f, 0.3f, 0.3f);
|
material.setBoolean("VertexLighting", true);
|
||||||
}
|
material.setFloat("Shininess", 127);
|
||||||
|
material.setBoolean("LowQuality", true);
|
||||||
|
material.setTexture("DiffuseMap", texture);
|
||||||
|
} else {
|
||||||
|
material = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
|
||||||
|
material.setTexture("ColorMap", texture);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
material = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
|
||||||
|
material.setColor("Color", ColorRGBA.Red);
|
||||||
|
}
|
||||||
|
|
||||||
// ModelConverter.optimize(geom);
|
TangentBinormalGenerator.generate(shape);
|
||||||
|
|
||||||
Texture texture = assetManager.loadTexture(new TextureKey("icons/textured.png"));
|
for (int y = -1; y < 2; y++) {
|
||||||
|
for (int x = -1; x < 2; x++) {
|
||||||
|
// int x = 0;
|
||||||
|
// int y = 0;
|
||||||
|
Geometry geomClone = new Geometry("geometry-" + y + "-" + x, shape);
|
||||||
|
geomClone.setMaterial(material);
|
||||||
|
geomClone.setLocalTranslation(x, y, 0);
|
||||||
|
|
||||||
Material material = null;
|
|
||||||
|
|
||||||
if (texturedEnabled) {
|
|
||||||
if (lightingEnabled) {
|
|
||||||
material = new Material(assetManager, "Common/MatDefs/Light/Lighting.j3md");
|
|
||||||
material.setBoolean("VertexLighting", true);
|
|
||||||
material.setFloat("Shininess", 127);
|
|
||||||
material.setBoolean("LowQuality", true);
|
|
||||||
material.setTexture("DiffuseMap", texture);
|
|
||||||
} else {
|
|
||||||
material = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
|
|
||||||
material.setTexture("ColorMap", texture);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
material = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
|
|
||||||
material.setColor("Color", ColorRGBA.Red);
|
|
||||||
}
|
|
||||||
|
|
||||||
TangentBinormalGenerator.generate(shape);
|
|
||||||
|
|
||||||
for (int y = -1; y < 2; y++) {
|
|
||||||
for (int x = -1; x < 2; x++){
|
|
||||||
// int x = 0;
|
|
||||||
// int y = 0;
|
|
||||||
Geometry geomClone = new Geometry("geometry-" + y + "-" + x, shape);
|
|
||||||
geomClone.setMaterial(material);
|
|
||||||
geomClone.setLocalTranslation(x, y, 0);
|
|
||||||
|
|
||||||
// Transform t = geom.getLocalTransform().clone();
|
// Transform t = geom.getLocalTransform().clone();
|
||||||
// Transform t2 = geomClone.getLocalTransform().clone();
|
// Transform t2 = geomClone.getLocalTransform().clone();
|
||||||
// t.combineWithParent(t2);
|
// t.combineWithParent(t2);
|
||||||
// geomClone.setLocalTransform(t);
|
// geomClone.setLocalTransform(t);
|
||||||
|
|
||||||
spheresContainer.attachChild(geomClone);
|
spheresContainer.attachChild(geomClone);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
spheresContainer.setLocalTranslation(new Vector3f(0, 0, -4f));
|
spheresContainer.setLocalTranslation(new Vector3f(0, 0, -4f));
|
||||||
spheresContainer.setLocalScale(2.0f);
|
spheresContainer.setLocalScale(2.0f);
|
||||||
|
|
||||||
rootNode.attachChild(spheresContainer);
|
rootNode.attachChild(spheresContainer);
|
||||||
|
|
||||||
PointLight pointLight = new PointLight();
|
PointLight pointLight = new PointLight();
|
||||||
|
|
||||||
pointLight.setColor(new ColorRGBA(0.7f, 0.7f, 1.0f, 1.0f));
|
pointLight.setColor(new ColorRGBA(0.7f, 0.7f, 1.0f, 1.0f));
|
||||||
|
|
||||||
pointLight.setPosition(new Vector3f(0f, 0f, 0f));
|
pointLight.setPosition(new Vector3f(0f, 0f, 0f));
|
||||||
pointLight.setRadius(8);
|
pointLight.setRadius(8);
|
||||||
|
|
||||||
rootNode.addLight(pointLight);
|
rootNode.addLight(pointLight);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void simpleUpdate(float tpf) {
|
public void simpleUpdate(float tpf) {
|
||||||
|
|
||||||
if (secondCounter == 0)
|
if (secondCounter == 0) {
|
||||||
logger.info("Frames per second: " + timer.getFrameRate());
|
logger.info("Frames per second: " + timer.getFrameRate());
|
||||||
|
}
|
||||||
spheresContainer.rotate(0.2f * tpf, 0.4f * tpf, 0.8f * tpf);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
spheresContainer.rotate(0.2f * tpf, 0.4f * tpf, 0.8f * tpf);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -15,19 +15,19 @@ public class Test extends SimpleApplication {
|
|||||||
public void simpleInitApp() {
|
public void simpleInitApp() {
|
||||||
Sphere s = new Sphere(8, 8, .5f);
|
Sphere s = new Sphere(8, 8, .5f);
|
||||||
Geometry geom = new Geometry("sphere", s);
|
Geometry geom = new Geometry("sphere", s);
|
||||||
// ModelConverter.optimize(geom);
|
// ModelConverter.optimize(geom);
|
||||||
|
|
||||||
Material mat = new Material(assetManager, "plain_texture.j3md");
|
Material mat = new Material(assetManager, "plain_texture.j3md");
|
||||||
Texture tex = assetManager.loadTexture(new TextureKey("monkey.j3i"));
|
Texture tex = assetManager.loadTexture(new TextureKey("monkey.j3i"));
|
||||||
mat.setTexture("ColorMap", tex);
|
mat.setTexture("ColorMap", tex);
|
||||||
// geom.setMaterial(mat);
|
// geom.setMaterial(mat);
|
||||||
|
|
||||||
for (int y = -1; y < 2; y++){
|
for (int y = -1; y < 2; y++) {
|
||||||
for (int x = -1; x < 2; x++){
|
for (int x = -1; x < 2; x++) {
|
||||||
Geometry geomClone = new Geometry("geom", s);
|
Geometry geomClone = new Geometry("geom", s);
|
||||||
geomClone.setMaterial(mat);
|
geomClone.setMaterial(mat);
|
||||||
geomClone.setLocalTranslation(x, y, 0);
|
geomClone.setLocalTranslation(x, y, 0);
|
||||||
|
|
||||||
Transform t = geom.getLocalTransform().clone();
|
Transform t = geom.getLocalTransform().clone();
|
||||||
Transform t2 = geomClone.getLocalTransform().clone();
|
Transform t2 = geomClone.getLocalTransform().clone();
|
||||||
t.combineWithParent(t2);
|
t.combineWithParent(t2);
|
||||||
@ -37,5 +37,4 @@ public class Test extends SimpleApplication {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -7,14 +7,13 @@ import com.jme3.scene.Node;
|
|||||||
import com.jme3.scene.Spatial;
|
import com.jme3.scene.Spatial;
|
||||||
import com.jme3.scene.Spatial.CullHint;
|
import com.jme3.scene.Spatial.CullHint;
|
||||||
|
|
||||||
|
|
||||||
public class TestSceneLoading extends SimpleApplication {
|
public class TestSceneLoading extends SimpleApplication {
|
||||||
|
|
||||||
private void setState(Spatial s){
|
private void setState(Spatial s) {
|
||||||
s.setCullHint(CullHint.Never);
|
s.setCullHint(CullHint.Never);
|
||||||
if (s instanceof Node){
|
if (s instanceof Node) {
|
||||||
Node n = (Node) s;
|
Node n = (Node) s;
|
||||||
for (int i = 0; i < n.getQuantity(); i++){
|
for (int i = 0; i < n.getQuantity(); i++) {
|
||||||
Spatial s2 = n.getChild(i);
|
Spatial s2 = n.getChild(i);
|
||||||
setState(s2);
|
setState(s2);
|
||||||
}
|
}
|
||||||
@ -22,16 +21,15 @@ public class TestSceneLoading extends SimpleApplication {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void simpleInitApp() {
|
public void simpleInitApp() {
|
||||||
/* XXX: does not compile */
|
/* XXX: does not compile */
|
||||||
|
|
||||||
/* Spatial scene = inputManager.loadModel("FINAL_LEVEL2.j3o");
|
/* Spatial scene = inputManager.loadModel("FINAL_LEVEL2.j3o");
|
||||||
// setState(scene);
|
// setState(scene);
|
||||||
rootNode.attachChild(scene);
|
rootNode.attachChild(scene);
|
||||||
|
|
||||||
cam.setLocation(new Vector3f(-18.059685f, 34.64228f, 4.5048084f));
|
cam.setLocation(new Vector3f(-18.059685f, 34.64228f, 4.5048084f));
|
||||||
cam.setRotation(new Quaternion(0.22396432f, 0.5235024f, -0.1448922f, 0.8091919f));
|
cam.setRotation(new Quaternion(0.22396432f, 0.5235024f, -0.1448922f, 0.8091919f));
|
||||||
cam.update();
|
cam.update();
|
||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,6 +1,5 @@
|
|||||||
package jme3test.android;
|
package jme3test.android;
|
||||||
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
@ -30,152 +29,143 @@ import jme3test.android.AndroidActivity;
|
|||||||
|
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
|
|
||||||
|
|
||||||
public class TestsActivity extends Activity {
|
public class TestsActivity extends Activity {
|
||||||
|
|
||||||
private static final java.util.logging.Logger logger = java.util.logging.Logger.getLogger(TestsActivity.class.getName());
|
private static final java.util.logging.Logger logger = java.util.logging.Logger.getLogger(TestsActivity.class.getName());
|
||||||
|
|
||||||
|
public static class Test {
|
||||||
|
|
||||||
|
private String name = null;
|
||||||
|
private String className = null;
|
||||||
|
|
||||||
|
public Test(String name, String className) {
|
||||||
|
this.name = name;
|
||||||
|
this.className = className;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getClassName() {
|
||||||
|
return className;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
private final static Test[] tests = {
|
||||||
|
new Test("SimpleTextured", "jme3test.android.SimpleTexturedTest"),
|
||||||
|
new Test("light.TestLightRadius", "jme3test.light.TestLightRadius"),
|
||||||
|
new Test("bullet.TestSimplePhysics", "jme3test.bullet.TestSimplePhysics"),
|
||||||
|
new Test("helloworld.HelloJME3", "jme3test.helloworld.HelloJME3"),
|
||||||
|
new Test("helloworld.HelloLoop", "jme3test.helloworld.HelloLoop"),
|
||||||
|
new Test("helloworld.HelloNode", "jme3test.helloworld.HelloNode"),
|
||||||
|
new Test("helloworld.HelloEffects", "jme3test.helloworld.HelloEffects"),
|
||||||
|
new Test("helloworld.HelloTerrain", "jme3test.helloworld.HelloTerrain")
|
||||||
|
};
|
||||||
|
private boolean useVA;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onCreate(Bundle savedInstanceState) {
|
||||||
|
logger.info("onCreate(" + savedInstanceState + ")");
|
||||||
|
|
||||||
|
super.onCreate(savedInstanceState);
|
||||||
|
|
||||||
|
//setContentView(R.layout.tests);
|
||||||
|
|
||||||
|
try {
|
||||||
|
|
||||||
|
useVA = true;
|
||||||
|
|
||||||
|
//LinearLayout buttonsContainer = (LinearLayout) findViewById(R.id.buttonsContainer);
|
||||||
|
|
||||||
|
|
||||||
public static class Test {
|
for (Test test : tests) {
|
||||||
|
final Button button = new Button(this);
|
||||||
|
final String finalName = test.getName();
|
||||||
|
final String finalClassName = test.getClassName();
|
||||||
|
|
||||||
private String name = null;
|
button.setText(test.getName());
|
||||||
private String className = null;
|
|
||||||
|
|
||||||
public Test(String name, String className) {
|
|
||||||
this.name = name;
|
|
||||||
this.className = className;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getName() {
|
|
||||||
return name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getClassName() {
|
|
||||||
return className;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private final static Test[] tests = {
|
|
||||||
new Test("SimpleTextured", "jme3test.android.SimpleTexturedTest"),
|
|
||||||
new Test("light.TestLightRadius", "jme3test.light.TestLightRadius"),
|
|
||||||
new Test("bullet.TestSimplePhysics", "jme3test.bullet.TestSimplePhysics"),
|
|
||||||
new Test("helloworld.HelloJME3", "jme3test.helloworld.HelloJME3"),
|
|
||||||
new Test("helloworld.HelloLoop", "jme3test.helloworld.HelloLoop"),
|
|
||||||
new Test("helloworld.HelloNode", "jme3test.helloworld.HelloNode"),
|
|
||||||
new Test("helloworld.HelloEffects", "jme3test.helloworld.HelloEffects"),
|
|
||||||
new Test("helloworld.HelloTerrain", "jme3test.helloworld.HelloTerrain")
|
|
||||||
};
|
|
||||||
|
|
||||||
private boolean useVA;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onCreate(Bundle savedInstanceState) {
|
|
||||||
logger.info("onCreate(" + savedInstanceState + ")");
|
|
||||||
|
|
||||||
super.onCreate(savedInstanceState);
|
|
||||||
|
|
||||||
//setContentView(R.layout.tests);
|
|
||||||
|
|
||||||
try {
|
|
||||||
|
|
||||||
useVA = true;
|
|
||||||
|
|
||||||
//LinearLayout buttonsContainer = (LinearLayout) findViewById(R.id.buttonsContainer);
|
|
||||||
|
|
||||||
|
|
||||||
for (Test test: tests) {
|
|
||||||
final Button button = new Button(this);
|
|
||||||
final String finalName = test.getName();
|
|
||||||
final String finalClassName = test.getClassName();
|
|
||||||
|
|
||||||
button.setText(test.getName());
|
|
||||||
// button.setTextSize(10.0f);
|
// button.setTextSize(10.0f);
|
||||||
// button.setTextColor(Color.rgb(100, 200, 200));
|
// button.setTextColor(Color.rgb(100, 200, 200));
|
||||||
//buttonsContainer.addView(button);
|
//buttonsContainer.addView(button);
|
||||||
|
|
||||||
button.setOnClickListener(
|
button.setOnClickListener(
|
||||||
new View.OnClickListener() {
|
new View.OnClickListener() {
|
||||||
@Override
|
|
||||||
public void onClick(View view) {
|
|
||||||
Intent intent = new Intent(view.getContext(), AndroidActivity.class);
|
|
||||||
intent.putExtra(AndroidActivity.class.getName() + ".TEST_CLASS_NAME", finalClassName);
|
|
||||||
intent.putExtra(AndroidActivity.class.getName() + ".USE_VA", useVA);
|
|
||||||
startActivityForResult(intent, 0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
} catch (Exception exception) {
|
|
||||||
logger.warning("exception: " + exception);
|
|
||||||
exception.printStackTrace(System.err);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onDestroy() {
|
public void onClick(View view) {
|
||||||
logger.info("onDestroy()");
|
Intent intent = new Intent(view.getContext(), AndroidActivity.class);
|
||||||
super.onDestroy();
|
intent.putExtra(AndroidActivity.class.getName() + ".TEST_CLASS_NAME", finalClassName);
|
||||||
}
|
intent.putExtra(AndroidActivity.class.getName() + ".USE_VA", useVA);
|
||||||
|
startActivityForResult(intent, 0);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} catch (Exception exception) {
|
||||||
|
logger.warning("exception: " + exception);
|
||||||
|
exception.printStackTrace(System.err);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onDestroy() {
|
||||||
|
logger.info("onDestroy()");
|
||||||
|
super.onDestroy();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onResume() {
|
protected void onResume() {
|
||||||
super.onResume();
|
super.onResume();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onStart() {
|
|
||||||
super.onStart();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onStop() {
|
protected void onStart() {
|
||||||
super.onStop();
|
super.onStart();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean onCreateOptionsMenu(Menu menu) {
|
protected void onStop() {
|
||||||
MenuInflater inflater = getMenuInflater();
|
super.onStop();
|
||||||
//inflater.inflate(R.menu.options, menu);
|
}
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean onOptionsItemSelected(MenuItem item) {
|
public boolean onCreateOptionsMenu(Menu menu) {
|
||||||
/*
|
MenuInflater inflater = getMenuInflater();
|
||||||
switch (item.getItemId()) {
|
//inflater.inflate(R.menu.options, menu);
|
||||||
case R.id.about_button:
|
return true;
|
||||||
about();
|
}
|
||||||
return true;
|
|
||||||
case R.id.quit_button:
|
|
||||||
quit();
|
|
||||||
return true;
|
|
||||||
default:
|
|
||||||
return super.onOptionsItemSelected(item);
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void quit() {
|
@Override
|
||||||
finish();
|
public boolean onOptionsItemSelected(MenuItem item) {
|
||||||
}
|
/*
|
||||||
|
switch (item.getItemId()) {
|
||||||
private void about() {
|
case R.id.about_button:
|
||||||
// Intent intent = new Intent(getView().getContext(), AboutActivity.class);
|
about();
|
||||||
try {
|
return true;
|
||||||
Intent intent = new Intent();
|
case R.id.quit_button:
|
||||||
intent.setClassName(
|
quit();
|
||||||
"jme3test.android",
|
return true;
|
||||||
"jme3test.android.AboutActivity"
|
default:
|
||||||
);
|
return super.onOptionsItemSelected(item);
|
||||||
startActivity(intent);
|
}
|
||||||
} catch (Exception exception) {
|
*/
|
||||||
logger.warning("exception: " + exception);
|
return false;
|
||||||
exception.printStackTrace(System.err);
|
}
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
private void quit() {
|
||||||
|
finish();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void about() {
|
||||||
|
// Intent intent = new Intent(getView().getContext(), AboutActivity.class);
|
||||||
|
try {
|
||||||
|
Intent intent = new Intent();
|
||||||
|
intent.setClassName(
|
||||||
|
"jme3test.android",
|
||||||
|
"jme3test.android.AboutActivity");
|
||||||
|
startActivity(intent);
|
||||||
|
} catch (Exception exception) {
|
||||||
|
logger.warning("exception: " + exception);
|
||||||
|
exception.printStackTrace(System.err);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -14,424 +14,413 @@ import java.util.Random;
|
|||||||
* @author CW
|
* @author CW
|
||||||
*/
|
*/
|
||||||
public final class Fixed {
|
public final class Fixed {
|
||||||
/**
|
|
||||||
* Number of bits used for 'fraction'.
|
|
||||||
*/
|
|
||||||
public static final int FIXED_POINT = 16;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Decimal one as represented by the Fixed class.
|
* Number of bits used for 'fraction'.
|
||||||
*/
|
*/
|
||||||
public static final int ONE = 1 << FIXED_POINT;
|
public static final int FIXED_POINT = 16;
|
||||||
|
/**
|
||||||
|
* Decimal one as represented by the Fixed class.
|
||||||
|
*/
|
||||||
|
public static final int ONE = 1 << FIXED_POINT;
|
||||||
|
/**
|
||||||
|
* Half in fixed point.
|
||||||
|
*/
|
||||||
|
public static final int HALF = ONE >> 1;
|
||||||
|
/**
|
||||||
|
* Quarter circle resolution for trig functions (should be a power of
|
||||||
|
* two). This is the number of discrete steps in 90 degrees.
|
||||||
|
*/
|
||||||
|
public static final int QUARTER_CIRCLE = 64;
|
||||||
|
/**
|
||||||
|
* Mask used to limit angles to one revolution. If a quarter circle is 64
|
||||||
|
* (i.e. 90 degrees is broken into 64 steps) then the mask is 255.
|
||||||
|
*/
|
||||||
|
public static final int FULL_CIRCLE_MASK = QUARTER_CIRCLE * 4 - 1;
|
||||||
|
/**
|
||||||
|
* The trig table is generated at a higher precision than the typical
|
||||||
|
* 16.16 format used for the rest of the fixed point maths. The table
|
||||||
|
* values are then shifted to match the actual fixed point used.
|
||||||
|
*/
|
||||||
|
private static final int TABLE_SHIFT = 30;
|
||||||
|
/**
|
||||||
|
* Equivalent to: sin((2 * PI) / (QUARTER_CIRCLE * 4))
|
||||||
|
* <p>
|
||||||
|
* Note: if either QUARTER_CIRCLE or TABLE_SHIFT is changed this value
|
||||||
|
* will need recalculating (put the above formular into a calculator set
|
||||||
|
* radians, then shift the result by <code>TABLE_SHIFT</code>).
|
||||||
|
*/
|
||||||
|
private static final int SIN_PRECALC = 26350943;
|
||||||
|
/**
|
||||||
|
* Equivalent to: cos((2 * PI) / (QUARTER_CIRCLE * 4)) * 2
|
||||||
|
*
|
||||||
|
* Note: if either QUARTER_CIRCLE or TABLE_SHIFT is changed this value
|
||||||
|
* will need recalculating ((put the above formular into a calculator set
|
||||||
|
* radians, then shift the result by <code>TABLE_SHIFT</code>).
|
||||||
|
*/
|
||||||
|
private static final int COS_PRECALC = 2146836866;
|
||||||
|
/**
|
||||||
|
* One quarter sine wave as fixed point values.
|
||||||
|
*/
|
||||||
|
private static final int[] SINE_TABLE = new int[QUARTER_CIRCLE + 1];
|
||||||
|
/**
|
||||||
|
* Scale value for indexing ATAN_TABLE[].
|
||||||
|
*/
|
||||||
|
private static final int ATAN_SHIFT;
|
||||||
|
/**
|
||||||
|
* Reverse atan lookup table.
|
||||||
|
*/
|
||||||
|
private static final byte[] ATAN_TABLE;
|
||||||
|
/**
|
||||||
|
* ATAN_TABLE.length
|
||||||
|
*/
|
||||||
|
private static final int ATAN_TABLE_LEN;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Half in fixed point.
|
* Generates the tables and fills in any remaining static ints.
|
||||||
*/
|
*/
|
||||||
public static final int HALF = ONE >> 1;
|
static {
|
||||||
|
// Generate the sine table using recursive synthesis.
|
||||||
|
SINE_TABLE[0] = 0;
|
||||||
|
SINE_TABLE[1] = SIN_PRECALC;
|
||||||
|
for (int n = 2; n < QUARTER_CIRCLE + 1; n++) {
|
||||||
|
SINE_TABLE[n] = (int) (((long) SINE_TABLE[n - 1] * COS_PRECALC) >> TABLE_SHIFT) - SINE_TABLE[n - 2];
|
||||||
|
}
|
||||||
|
// Scale the values to the fixed point format used.
|
||||||
|
for (int n = 0; n < QUARTER_CIRCLE + 1; n++) {
|
||||||
|
SINE_TABLE[n] = SINE_TABLE[n] + (1 << (TABLE_SHIFT - FIXED_POINT - 1)) >> TABLE_SHIFT - FIXED_POINT;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
// Calculate a shift used to scale atan lookups
|
||||||
* Quarter circle resolution for trig functions (should be a power of
|
int rotl = 0;
|
||||||
* two). This is the number of discrete steps in 90 degrees.
|
int tan0 = tan(0);
|
||||||
*/
|
int tan1 = tan(1);
|
||||||
public static final int QUARTER_CIRCLE = 64;
|
while (rotl < 32) {
|
||||||
|
if ((tan1 >>= 1) > (tan0 >>= 1)) {
|
||||||
|
rotl++;
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ATAN_SHIFT = rotl;
|
||||||
|
// Create the a table of tan values
|
||||||
|
int[] lut = new int[QUARTER_CIRCLE];
|
||||||
|
for (int n = 0; n < QUARTER_CIRCLE; n++) {
|
||||||
|
lut[n] = tan(n) >> rotl;
|
||||||
|
}
|
||||||
|
ATAN_TABLE_LEN = lut[QUARTER_CIRCLE - 1];
|
||||||
|
// Then from the tan values create a reverse lookup
|
||||||
|
ATAN_TABLE = new byte[ATAN_TABLE_LEN];
|
||||||
|
for (byte n = 0; n < QUARTER_CIRCLE - 1; n++) {
|
||||||
|
int min = lut[n];
|
||||||
|
int max = lut[n + 1];
|
||||||
|
for (int i = min; i < max; i++) {
|
||||||
|
ATAN_TABLE[i] = n;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* How many decimal places to use when converting a fixed point value to
|
||||||
|
* a decimal string.
|
||||||
|
*
|
||||||
|
* @see #toString
|
||||||
|
*/
|
||||||
|
private static final int STRING_DECIMAL_PLACES = 2;
|
||||||
|
/**
|
||||||
|
* Value to add in order to round down a fixed point number when
|
||||||
|
* converting to a string.
|
||||||
|
*/
|
||||||
|
private static final int STRING_DECIMAL_PLACES_ROUND;
|
||||||
|
|
||||||
/**
|
static {
|
||||||
* Mask used to limit angles to one revolution. If a quarter circle is 64
|
int i = 10;
|
||||||
* (i.e. 90 degrees is broken into 64 steps) then the mask is 255.
|
for (int n = 1; n < STRING_DECIMAL_PLACES; n++) {
|
||||||
*/
|
i *= i;
|
||||||
public static final int FULL_CIRCLE_MASK = QUARTER_CIRCLE * 4 - 1;
|
}
|
||||||
|
if (STRING_DECIMAL_PLACES == 0) {
|
||||||
|
STRING_DECIMAL_PLACES_ROUND = ONE / 2;
|
||||||
|
} else {
|
||||||
|
STRING_DECIMAL_PLACES_ROUND = ONE / (2 * i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Random number generator. The standard <code>java.utll.Random</code> is
|
||||||
|
* used since it is available to both J2ME and J2SE. If a guaranteed
|
||||||
|
* sequence is required this would not be adequate.
|
||||||
|
*/
|
||||||
|
private static Random rng = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The trig table is generated at a higher precision than the typical
|
* Fixed can't be instantiated.
|
||||||
* 16.16 format used for the rest of the fixed point maths. The table
|
*/
|
||||||
* values are then shifted to match the actual fixed point used.
|
private Fixed() {
|
||||||
*/
|
}
|
||||||
private static final int TABLE_SHIFT = 30;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Equivalent to: sin((2 * PI) / (QUARTER_CIRCLE * 4))
|
* Returns an integer as a fixed point value.
|
||||||
* <p>
|
*/
|
||||||
* Note: if either QUARTER_CIRCLE or TABLE_SHIFT is changed this value
|
public static int intToFixed(int n) {
|
||||||
* will need recalculating (put the above formular into a calculator set
|
return n << FIXED_POINT;
|
||||||
* radians, then shift the result by <code>TABLE_SHIFT</code>).
|
}
|
||||||
*/
|
|
||||||
private static final int SIN_PRECALC = 26350943;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Equivalent to: cos((2 * PI) / (QUARTER_CIRCLE * 4)) * 2
|
|
||||||
*
|
|
||||||
* Note: if either QUARTER_CIRCLE or TABLE_SHIFT is changed this value
|
|
||||||
* will need recalculating ((put the above formular into a calculator set
|
|
||||||
* radians, then shift the result by <code>TABLE_SHIFT</code>).
|
|
||||||
*/
|
|
||||||
private static final int COS_PRECALC = 2146836866;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* One quarter sine wave as fixed point values.
|
|
||||||
*/
|
|
||||||
private static final int[] SINE_TABLE = new int[QUARTER_CIRCLE + 1];
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Scale value for indexing ATAN_TABLE[].
|
|
||||||
*/
|
|
||||||
private static final int ATAN_SHIFT;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Reverse atan lookup table.
|
|
||||||
*/
|
|
||||||
private static final byte[] ATAN_TABLE;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* ATAN_TABLE.length
|
|
||||||
*/
|
|
||||||
private static final int ATAN_TABLE_LEN;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Generates the tables and fills in any remaining static ints.
|
|
||||||
*/
|
|
||||||
static {
|
|
||||||
// Generate the sine table using recursive synthesis.
|
|
||||||
SINE_TABLE[0] = 0;
|
|
||||||
SINE_TABLE[1] = SIN_PRECALC;
|
|
||||||
for (int n = 2; n < QUARTER_CIRCLE + 1; n++) {
|
|
||||||
SINE_TABLE[n] = (int) (((long) SINE_TABLE[n - 1] * COS_PRECALC) >> TABLE_SHIFT) - SINE_TABLE[n - 2];
|
|
||||||
}
|
|
||||||
// Scale the values to the fixed point format used.
|
|
||||||
for (int n = 0; n < QUARTER_CIRCLE + 1; n++) {
|
|
||||||
SINE_TABLE[n] = SINE_TABLE[n] + (1 << (TABLE_SHIFT - FIXED_POINT - 1)) >> TABLE_SHIFT - FIXED_POINT;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Calculate a shift used to scale atan lookups
|
|
||||||
int rotl = 0;
|
|
||||||
int tan0 = tan(0);
|
|
||||||
int tan1 = tan(1);
|
|
||||||
while (rotl < 32) {
|
|
||||||
if ((tan1 >>= 1) > (tan0 >>= 1)) {
|
|
||||||
rotl++;
|
|
||||||
} else {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
ATAN_SHIFT = rotl;
|
|
||||||
// Create the a table of tan values
|
|
||||||
int[] lut = new int[QUARTER_CIRCLE];
|
|
||||||
for (int n = 0; n < QUARTER_CIRCLE; n++) {
|
|
||||||
lut[n] = tan(n) >> rotl;
|
|
||||||
}
|
|
||||||
ATAN_TABLE_LEN = lut[QUARTER_CIRCLE - 1];
|
|
||||||
// Then from the tan values create a reverse lookup
|
|
||||||
ATAN_TABLE = new byte[ATAN_TABLE_LEN];
|
|
||||||
for (byte n = 0; n < QUARTER_CIRCLE - 1; n++) {
|
|
||||||
int min = lut[n ];
|
|
||||||
int max = lut[n + 1];
|
|
||||||
for (int i = min; i < max; i++) {
|
|
||||||
ATAN_TABLE[i] = n;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* How many decimal places to use when converting a fixed point value to
|
|
||||||
* a decimal string.
|
|
||||||
*
|
|
||||||
* @see #toString
|
|
||||||
*/
|
|
||||||
private static final int STRING_DECIMAL_PLACES = 2;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Value to add in order to round down a fixed point number when
|
|
||||||
* converting to a string.
|
|
||||||
*/
|
|
||||||
private static final int STRING_DECIMAL_PLACES_ROUND;
|
|
||||||
static {
|
|
||||||
int i = 10;
|
|
||||||
for (int n = 1; n < STRING_DECIMAL_PLACES; n++) {
|
|
||||||
i *= i;
|
|
||||||
}
|
|
||||||
if (STRING_DECIMAL_PLACES == 0) {
|
|
||||||
STRING_DECIMAL_PLACES_ROUND = ONE / 2;
|
|
||||||
} else {
|
|
||||||
STRING_DECIMAL_PLACES_ROUND = ONE / (2 * i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Random number generator. The standard <code>java.utll.Random</code> is
|
|
||||||
* used since it is available to both J2ME and J2SE. If a guaranteed
|
|
||||||
* sequence is required this would not be adequate.
|
|
||||||
*/
|
|
||||||
private static Random rng = null;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Fixed can't be instantiated.
|
|
||||||
*/
|
|
||||||
private Fixed() {}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns an integer as a fixed point value.
|
|
||||||
*/
|
|
||||||
public static int intToFixed(int n) {
|
|
||||||
return n << FIXED_POINT;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a fixed point value as a float.
|
* Returns a fixed point value as a float.
|
||||||
*/
|
*/
|
||||||
public static float fixedToFloat(int i) {
|
public static float fixedToFloat(int i) {
|
||||||
float fp = i;
|
float fp = i;
|
||||||
fp = fp / ((float)ONE);
|
fp = fp / ((float) ONE);
|
||||||
return fp;
|
return fp;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a float as a fixed point value.
|
* Returns a float as a fixed point value.
|
||||||
*/
|
*/
|
||||||
public static int floatToFixed(float fp){
|
public static int floatToFixed(float fp) {
|
||||||
return (int) (fp * ((float) ONE));
|
return (int) (fp * ((float) ONE));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Converts a fixed point value into a decimal string.
|
* Converts a fixed point value into a decimal string.
|
||||||
*/
|
*/
|
||||||
public static String toString(int n) {
|
public static String toString(int n) {
|
||||||
StringBuffer sb = new StringBuffer(16);
|
StringBuffer sb = new StringBuffer(16);
|
||||||
sb.append((n += STRING_DECIMAL_PLACES_ROUND) >> FIXED_POINT);
|
sb.append((n += STRING_DECIMAL_PLACES_ROUND) >> FIXED_POINT);
|
||||||
sb.append('.');
|
sb.append('.');
|
||||||
n &= ONE - 1;
|
n &= ONE - 1;
|
||||||
for (int i = 0; i < STRING_DECIMAL_PLACES; i++) {
|
for (int i = 0; i < STRING_DECIMAL_PLACES; i++) {
|
||||||
n *= 10;
|
n *= 10;
|
||||||
sb.append((n / ONE) % 10);
|
sb.append((n / ONE) % 10);
|
||||||
}
|
}
|
||||||
return sb.toString();
|
return sb.toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Multiplies two fixed point values and returns the result.
|
* Multiplies two fixed point values and returns the result.
|
||||||
*/
|
*/
|
||||||
public static int mul(int a, int b) {
|
public static int mul(int a, int b) {
|
||||||
return (int) ((long) a * (long) b >> FIXED_POINT);
|
return (int) ((long) a * (long) b >> FIXED_POINT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Divides two fixed point values and returns the result.
|
* Divides two fixed point values and returns the result.
|
||||||
*/
|
*/
|
||||||
public static int div(int a, int b) {
|
public static int div(int a, int b) {
|
||||||
return (int) (((long) a << FIXED_POINT * 2) / (long) b >> FIXED_POINT);
|
return (int) (((long) a << FIXED_POINT * 2) / (long) b >> FIXED_POINT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sine of an angle.
|
* Sine of an angle.
|
||||||
*
|
*
|
||||||
* @see #QUARTER_CIRCLE
|
* @see #QUARTER_CIRCLE
|
||||||
*/
|
*/
|
||||||
public static int sin(int n) {
|
public static int sin(int n) {
|
||||||
n &= FULL_CIRCLE_MASK;
|
n &= FULL_CIRCLE_MASK;
|
||||||
if (n < QUARTER_CIRCLE * 2) {
|
if (n < QUARTER_CIRCLE * 2) {
|
||||||
if (n < QUARTER_CIRCLE) {
|
if (n < QUARTER_CIRCLE) {
|
||||||
return SINE_TABLE[n];
|
return SINE_TABLE[n];
|
||||||
} else {
|
} else {
|
||||||
return SINE_TABLE[QUARTER_CIRCLE * 2 - n];
|
return SINE_TABLE[QUARTER_CIRCLE * 2 - n];
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (n < QUARTER_CIRCLE * 3) {
|
if (n < QUARTER_CIRCLE * 3) {
|
||||||
return -SINE_TABLE[n - QUARTER_CIRCLE * 2];
|
return -SINE_TABLE[n - QUARTER_CIRCLE * 2];
|
||||||
} else {
|
} else {
|
||||||
return -SINE_TABLE[QUARTER_CIRCLE * 4 - n];
|
return -SINE_TABLE[QUARTER_CIRCLE * 4 - n];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Cosine of an angle.
|
* Cosine of an angle.
|
||||||
*
|
*
|
||||||
* @see #QUARTER_CIRCLE
|
* @see #QUARTER_CIRCLE
|
||||||
*/
|
*/
|
||||||
public static int cos(int n) {
|
public static int cos(int n) {
|
||||||
n &= FULL_CIRCLE_MASK;
|
n &= FULL_CIRCLE_MASK;
|
||||||
if (n < QUARTER_CIRCLE * 2) {
|
if (n < QUARTER_CIRCLE * 2) {
|
||||||
if (n < QUARTER_CIRCLE) {
|
if (n < QUARTER_CIRCLE) {
|
||||||
return SINE_TABLE[QUARTER_CIRCLE - n];
|
return SINE_TABLE[QUARTER_CIRCLE - n];
|
||||||
} else {
|
} else {
|
||||||
return -SINE_TABLE[n - QUARTER_CIRCLE];
|
return -SINE_TABLE[n - QUARTER_CIRCLE];
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (n < QUARTER_CIRCLE * 3) {
|
if (n < QUARTER_CIRCLE * 3) {
|
||||||
return -SINE_TABLE[QUARTER_CIRCLE * 3 - n];
|
return -SINE_TABLE[QUARTER_CIRCLE * 3 - n];
|
||||||
} else {
|
} else {
|
||||||
return SINE_TABLE[n - QUARTER_CIRCLE * 3];
|
return SINE_TABLE[n - QUARTER_CIRCLE * 3];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tangent of an angle.
|
* Tangent of an angle.
|
||||||
*
|
*
|
||||||
* @see #QUARTER_CIRCLE
|
* @see #QUARTER_CIRCLE
|
||||||
*/
|
*/
|
||||||
public static int tan(int n) {
|
public static int tan(int n) {
|
||||||
return div(sin(n), cos(n));
|
return div(sin(n), cos(n));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the arc tangent of an angle.
|
* Returns the arc tangent of an angle.
|
||||||
*/
|
*/
|
||||||
public static int atan(int n) {
|
public static int atan(int n) {
|
||||||
n = n + (1 << (ATAN_SHIFT - 1)) >> ATAN_SHIFT;
|
n = n + (1 << (ATAN_SHIFT - 1)) >> ATAN_SHIFT;
|
||||||
if (n < 0) {
|
if (n < 0) {
|
||||||
if (n <= -ATAN_TABLE_LEN) {
|
if (n <= -ATAN_TABLE_LEN) {
|
||||||
return -(QUARTER_CIRCLE - 1);
|
return -(QUARTER_CIRCLE - 1);
|
||||||
}
|
}
|
||||||
return -ATAN_TABLE[-n];
|
return -ATAN_TABLE[-n];
|
||||||
} else {
|
} else {
|
||||||
if (n >= ATAN_TABLE_LEN) {
|
if (n >= ATAN_TABLE_LEN) {
|
||||||
return QUARTER_CIRCLE - 1;
|
return QUARTER_CIRCLE - 1;
|
||||||
}
|
}
|
||||||
return ATAN_TABLE[n];
|
return ATAN_TABLE[n];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the polar angle of a rectangular coordinate.
|
* Returns the polar angle of a rectangular coordinate.
|
||||||
*/
|
*/
|
||||||
public static int atan(int x, int y) {
|
public static int atan(int x, int y) {
|
||||||
int n = atan(div(x, abs(y) + 1)); // kludge to prevent ArithmeticException
|
int n = atan(div(x, abs(y) + 1)); // kludge to prevent ArithmeticException
|
||||||
if (y > 0) {
|
if (y > 0) {
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
if (y < 0) {
|
if (y < 0) {
|
||||||
if (x < 0) {
|
if (x < 0) {
|
||||||
return -QUARTER_CIRCLE * 2 - n;
|
return -QUARTER_CIRCLE * 2 - n;
|
||||||
}
|
}
|
||||||
if (x > 0) {
|
if (x > 0) {
|
||||||
return QUARTER_CIRCLE * 2 - n;
|
return QUARTER_CIRCLE * 2 - n;
|
||||||
}
|
}
|
||||||
return QUARTER_CIRCLE * 2;
|
return QUARTER_CIRCLE * 2;
|
||||||
}
|
}
|
||||||
if (x > 0) {
|
if (x > 0) {
|
||||||
return QUARTER_CIRCLE;
|
return QUARTER_CIRCLE;
|
||||||
}
|
}
|
||||||
return -QUARTER_CIRCLE;
|
return -QUARTER_CIRCLE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Rough calculation of the hypotenuse. Whilst not accurate it is very fast.
|
* Rough calculation of the hypotenuse. Whilst not accurate it is very fast.
|
||||||
* <p>
|
* <p>
|
||||||
* Derived from a piece in Graphics Gems.
|
* Derived from a piece in Graphics Gems.
|
||||||
*/
|
*/
|
||||||
public static int hyp(int x1, int y1, int x2, int y2) {
|
public static int hyp(int x1, int y1, int x2, int y2) {
|
||||||
if ((x2 -= x1) < 0) {
|
if ((x2 -= x1) < 0) {
|
||||||
x2 = -x2;
|
x2 = -x2;
|
||||||
}
|
}
|
||||||
if ((y2 -= y1) < 0) {
|
if ((y2 -= y1) < 0) {
|
||||||
y2 = -y2;
|
y2 = -y2;
|
||||||
}
|
}
|
||||||
return x2 + y2 - (((x2 > y2) ? y2 : x2) >> 1);
|
return x2 + y2 - (((x2 > y2) ? y2 : x2) >> 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Fixed point square root.
|
* Fixed point square root.
|
||||||
* <p>
|
* <p>
|
||||||
* Derived from a 1993 Usenet algorithm posted by Christophe Meessen.
|
* Derived from a 1993 Usenet algorithm posted by Christophe Meessen.
|
||||||
*/
|
*/
|
||||||
public static int sqrt(int n) {
|
public static int sqrt(int n) {
|
||||||
if (n <= 0) {
|
if (n <= 0) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
long sum = 0;
|
long sum = 0;
|
||||||
int bit = 0x40000000;
|
int bit = 0x40000000;
|
||||||
while (bit >= 0x100) { // lower values give more accurate results
|
while (bit >= 0x100) { // lower values give more accurate results
|
||||||
long tmp = sum | bit;
|
long tmp = sum | bit;
|
||||||
if (n >= tmp) {
|
if (n >= tmp) {
|
||||||
n -= tmp;
|
n -= tmp;
|
||||||
sum = tmp + bit;
|
sum = tmp + bit;
|
||||||
}
|
}
|
||||||
bit >>= 1;
|
bit >>= 1;
|
||||||
n <<= 1;
|
n <<= 1;
|
||||||
}
|
}
|
||||||
return (int) (sum >> 16 - (FIXED_POINT / 2));
|
return (int) (sum >> 16 - (FIXED_POINT / 2));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the absolute value.
|
* Returns the absolute value.
|
||||||
*/
|
*/
|
||||||
public static int abs(int n) {
|
public static int abs(int n) {
|
||||||
return (n < 0) ? -n : n;
|
return (n < 0) ? -n : n;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the sign of a value, -1 for negative numbers, otherwise 1.
|
* Returns the sign of a value, -1 for negative numbers, otherwise 1.
|
||||||
*/
|
*/
|
||||||
public static int sgn(int n) {
|
public static int sgn(int n) {
|
||||||
return (n < 0) ? -1 : 1;
|
return (n < 0) ? -1 : 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the minimum of two values.
|
* Returns the minimum of two values.
|
||||||
*/
|
*/
|
||||||
public static int min(int a, int b) {
|
public static int min(int a, int b) {
|
||||||
return (a < b) ? a : b;
|
return (a < b) ? a : b;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the maximum of two values.
|
* Returns the maximum of two values.
|
||||||
*/
|
*/
|
||||||
public static int max(int a, int b) {
|
public static int max(int a, int b) {
|
||||||
return (a > b) ? a : b;
|
return (a > b) ? a : b;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Clamps the value n between min and max.
|
* Clamps the value n between min and max.
|
||||||
*/
|
*/
|
||||||
public static int clamp(int n, int min, int max) {
|
public static int clamp(int n, int min, int max) {
|
||||||
return (n < min) ? min : (n > max) ? max : n;
|
return (n < min) ? min : (n > max) ? max : n;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Wraps the value n between 0 and the required limit.
|
* Wraps the value n between 0 and the required limit.
|
||||||
*/
|
*/
|
||||||
public static int wrap(int n, int limit) {
|
public static int wrap(int n, int limit) {
|
||||||
return ((n %= limit) < 0) ? limit + n : n;
|
return ((n %= limit) < 0) ? limit + n : n;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the nearest int to a fixed point value. Equivalent to <code>
|
* Returns the nearest int to a fixed point value. Equivalent to <code>
|
||||||
* Math.round()</code> in the standard library.
|
* Math.round()</code> in the standard library.
|
||||||
*/
|
*/
|
||||||
public static int round(int n) {
|
public static int round(int n) {
|
||||||
return n + HALF >> FIXED_POINT;
|
return n + HALF >> FIXED_POINT;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the nearest int rounded down from a fixed point value.
|
* Returns the nearest int rounded down from a fixed point value.
|
||||||
* Equivalent to <code>Math.floor()</code> in the standard library.
|
* Equivalent to <code>Math.floor()</code> in the standard library.
|
||||||
*/
|
*/
|
||||||
public static int floor(int n) {
|
public static int floor(int n) {
|
||||||
return n >> FIXED_POINT;
|
return n >> FIXED_POINT;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the nearest int rounded up from a fixed point value.
|
* Returns the nearest int rounded up from a fixed point value.
|
||||||
* Equivalent to <code>Math.ceil()</code> in the standard library.
|
* Equivalent to <code>Math.ceil()</code> in the standard library.
|
||||||
*/
|
*/
|
||||||
public static int ceil(int n) {
|
public static int ceil(int n) {
|
||||||
return n + (ONE - 1) >> FIXED_POINT;
|
return n + (ONE - 1) >> FIXED_POINT;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a fixed point value greater than or equal to decimal 0.0 and
|
* Returns a fixed point value greater than or equal to decimal 0.0 and
|
||||||
* less than 1.0 (in 16.16 format this would be 0 to 65535 inclusive).
|
* less than 1.0 (in 16.16 format this would be 0 to 65535 inclusive).
|
||||||
*/
|
*/
|
||||||
public static int rand() {
|
public static int rand() {
|
||||||
if (rng == null) {
|
if (rng == null) {
|
||||||
rng = new Random();
|
rng = new Random();
|
||||||
}
|
}
|
||||||
return rng.nextInt() >>> (32 - FIXED_POINT);
|
return rng.nextInt() >>> (32 - FIXED_POINT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a random number between 0 and <code>n</code> (exclusive).
|
* Returns a random number between 0 and <code>n</code> (exclusive).
|
||||||
*/
|
*/
|
||||||
public static int rand(int n) {
|
public static int rand(int n) {
|
||||||
return (rand() * n) >> FIXED_POINT;
|
return (rand() * n) >> FIXED_POINT;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -7,25 +7,25 @@
|
|||||||
android:layout_height="fill_parent"
|
android:layout_height="fill_parent"
|
||||||
>
|
>
|
||||||
|
|
||||||
<LinearLayout
|
<LinearLayout
|
||||||
android:id="@+id/buttonsContainer"
|
android:id="@+id/buttonsContainer"
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
android:orientation="vertical"
|
android:orientation="vertical"
|
||||||
android:layout_width="fill_parent"
|
android:layout_width="fill_parent"
|
||||||
android:layout_height="fill_parent"
|
android:layout_height="fill_parent"
|
||||||
>
|
>
|
||||||
<TextView
|
<TextView
|
||||||
android:layout_width="fill_parent"
|
android:layout_width="fill_parent"
|
||||||
android:layout_height="wrap_content"
|
android:layout_height="wrap_content"
|
||||||
android:text="copyright (c) 2009-2010 JMonkeyEngine"
|
android:text="copyright (c) 2009-2010 JMonkeyEngine"
|
||||||
/>
|
/>
|
||||||
|
|
||||||
<TextView
|
<TextView
|
||||||
android:layout_width="fill_parent"
|
android:layout_width="fill_parent"
|
||||||
android:layout_height="wrap_content"
|
android:layout_height="wrap_content"
|
||||||
android:text="http://www.jmonkeyengine.org"
|
android:text="http://www.jmonkeyengine.org"
|
||||||
/>
|
/>
|
||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|||||||
@ -6,14 +6,12 @@
|
|||||||
android:layout_width="fill_parent"
|
android:layout_width="fill_parent"
|
||||||
android:layout_height="fill_parent"
|
android:layout_height="fill_parent"
|
||||||
>
|
>
|
||||||
|
<LinearLayout
|
||||||
<LinearLayout
|
|
||||||
android:id="@+id/buttonsContainer"
|
android:id="@+id/buttonsContainer"
|
||||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
android:orientation="vertical"
|
android:orientation="vertical"
|
||||||
android:layout_width="fill_parent"
|
android:layout_width="fill_parent"
|
||||||
android:layout_height="fill_parent"
|
android:layout_height="fill_parent">
|
||||||
>
|
|
||||||
<!--
|
<!--
|
||||||
<Button
|
<Button
|
||||||
android:id="@+id/SimpleTextured"
|
android:id="@+id/SimpleTextured"
|
||||||
@ -23,6 +21,5 @@
|
|||||||
android:layout_weight="1"
|
android:layout_weight="1"
|
||||||
/>
|
/>
|
||||||
-->
|
-->
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|||||||
@ -1,14 +1,12 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<menu xmlns:android="http://schemas.android.com/apk/res/android">
|
<menu xmlns:android="http://schemas.android.com/apk/res/android">
|
||||||
|
<item
|
||||||
<item
|
android:id="@+id/about_button"
|
||||||
android:id="@+id/about_button"
|
android:title="@string/about"
|
||||||
android:title="@string/about"
|
|
||||||
/>
|
/>
|
||||||
|
|
||||||
<item
|
<item
|
||||||
android:id="@+id/quit_button"
|
android:id="@+id/quit_button"
|
||||||
android:title="@string/quit"
|
android:title="@string/quit"
|
||||||
/>
|
/>
|
||||||
|
|
||||||
</menu>
|
</menu>
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<resources>
|
<resources>
|
||||||
<string name="app_name">JMEAndroidTest</string>
|
<string name="app_name">JMEAndroidTest</string>
|
||||||
<string name="about">About</string>
|
<string name="about">About</string>
|
||||||
<string name="quit">Quit</string>
|
<string name="quit">Quit</string>
|
||||||
</resources>
|
</resources>
|
||||||
|
|||||||
@ -37,7 +37,6 @@ import com.jme3.input.KeyInput;
|
|||||||
import com.jme3.input.MouseInput;
|
import com.jme3.input.MouseInput;
|
||||||
import com.jme3.input.TouchInput;
|
import com.jme3.input.TouchInput;
|
||||||
import com.jme3.renderer.Renderer;
|
import com.jme3.renderer.Renderer;
|
||||||
import com.jme3.system.JmeCanvasContext;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents a rendering context within the engine.
|
* Represents a rendering context within the engine.
|
||||||
|
|||||||
65
engine/src/core/com/jme3/system/Platform.java
Normal file
65
engine/src/core/com/jme3/system/Platform.java
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
package com.jme3.system;
|
||||||
|
|
||||||
|
public enum Platform {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Microsoft Windows 32 bit
|
||||||
|
*/
|
||||||
|
Windows32,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Microsoft Windows 64 bit
|
||||||
|
*/
|
||||||
|
Windows64,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Linux 32 bit
|
||||||
|
*/
|
||||||
|
Linux32,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Linux 64 bit
|
||||||
|
*/
|
||||||
|
Linux64,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Apple Mac OS X 32 bit
|
||||||
|
*/
|
||||||
|
MacOSX32,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Apple Mac OS X 64 bit
|
||||||
|
*/
|
||||||
|
MacOSX64,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Apple Mac OS X 32 bit PowerPC
|
||||||
|
*/
|
||||||
|
MacOSX_PPC32,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Apple Mac OS X 64 bit PowerPC
|
||||||
|
*/
|
||||||
|
MacOSX_PPC64,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Android ARM5
|
||||||
|
*/
|
||||||
|
Android_ARM5,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Android ARM6
|
||||||
|
*/
|
||||||
|
Android_ARM6,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Android ARM7
|
||||||
|
*/
|
||||||
|
Android_ARM7,
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Android x86
|
||||||
|
*/
|
||||||
|
Android_X86;
|
||||||
|
|
||||||
|
}
|
||||||
@ -13,29 +13,75 @@ import com.jme3.texture.Image;
|
|||||||
import com.jme3.texture.Image.Format;
|
import com.jme3.texture.Image.Format;
|
||||||
import com.jme3.texture.Texture;
|
import com.jme3.texture.Texture;
|
||||||
import com.jme3.texture.TextureCubeMap;
|
import com.jme3.texture.TextureCubeMap;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* <code>SkyFactory</code> is used to create jME {@link Spatial}s that can
|
||||||
|
* be attached to the scene to display a sky image in the background.
|
||||||
|
*
|
||||||
|
* @author Kirill Vainer
|
||||||
|
*/
|
||||||
public class SkyFactory {
|
public class SkyFactory {
|
||||||
|
|
||||||
|
/**
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture texture, Vector3f normalScale, boolean sphereMap){
|
* Creates a sky using the given texture (cubemap or spheremap).
|
||||||
return createSky(assetManager, texture, normalScale, sphereMap, 10);
|
*
|
||||||
}
|
* @param assetManager The asset manager to use to load materials
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture texture, Vector3f normalScale, boolean sphereMap, int sphereRadius){
|
* @param texture Texture to use for the sky
|
||||||
if (texture == null)
|
* @param normalScale The normal scale is multiplied by the 3D normal
|
||||||
|
* to get a texture coordinate. Use Vector3f.UNIT_XYZ to not apply
|
||||||
|
* and transformation to the normal.
|
||||||
|
* @param sphereMap The way the texture is used
|
||||||
|
* depends on this value:<br>
|
||||||
|
* <ul>
|
||||||
|
* <li>true: Its a Texture2D with the pixels arranged for
|
||||||
|
* <a href="http://en.wikipedia.org/wiki/Sphere_mapping">sphere mapping</a>.</li>
|
||||||
|
* <li>false: Its either a TextureCubeMap or Texture2D. If its a Texture2D
|
||||||
|
* then the image is taken from it and is inserted into a TextureCubeMap</li>
|
||||||
|
* </ul>
|
||||||
|
* @return A spatial representing the sky
|
||||||
|
*/
|
||||||
|
public static Spatial createSky(AssetManager assetManager, Texture texture, Vector3f normalScale, boolean sphereMap) {
|
||||||
|
return createSky(assetManager, texture, normalScale, sphereMap, 10);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a sky using the given texture (cubemap or spheremap).
|
||||||
|
*
|
||||||
|
* @param assetManager The asset manager to use to load materials
|
||||||
|
* @param texture Texture to use for the sky
|
||||||
|
* @param normalScale The normal scale is multiplied by the 3D normal
|
||||||
|
* to get a texture coordinate. Use Vector3f.UNIT_XYZ to not apply
|
||||||
|
* and transformation to the normal.
|
||||||
|
* @param sphereMap The way the texture is used
|
||||||
|
* depends on this value:<br>
|
||||||
|
* <ul>
|
||||||
|
* <li>true: Its a Texture2D with the pixels arranged for
|
||||||
|
* <a href="http://en.wikipedia.org/wiki/Sphere_mapping">sphere mapping</a>.</li>
|
||||||
|
* <li>false: Its either a TextureCubeMap or Texture2D. If its a Texture2D
|
||||||
|
* then the image is taken from it and is inserted into a TextureCubeMap</li>
|
||||||
|
* </ul>
|
||||||
|
* @param sphereRadius If specified, this will be the sky sphere's radius.
|
||||||
|
* This should be the camera's near plane for optimal quality.
|
||||||
|
* @return A spatial representing the sky
|
||||||
|
*/
|
||||||
|
public static Spatial createSky(AssetManager assetManager, Texture texture, Vector3f normalScale, boolean sphereMap, int sphereRadius) {
|
||||||
|
if (texture == null) {
|
||||||
throw new IllegalArgumentException("texture cannot be null");
|
throw new IllegalArgumentException("texture cannot be null");
|
||||||
|
}
|
||||||
final Sphere sphereMesh = new Sphere(10, 10, sphereRadius, false, true);
|
final Sphere sphereMesh = new Sphere(10, 10, sphereRadius, false, true);
|
||||||
|
|
||||||
Geometry sky = new Geometry("Sky", sphereMesh);
|
Geometry sky = new Geometry("Sky", sphereMesh);
|
||||||
sky.setQueueBucket(Bucket.Sky);
|
sky.setQueueBucket(Bucket.Sky);
|
||||||
sky.setCullHint(Spatial.CullHint.Never);
|
sky.setCullHint(Spatial.CullHint.Never);
|
||||||
sky.setModelBound(new BoundingSphere(Float.POSITIVE_INFINITY, Vector3f.ZERO));
|
sky.setModelBound(new BoundingSphere(Float.POSITIVE_INFINITY, Vector3f.ZERO));
|
||||||
|
|
||||||
Material skyMat = new Material(assetManager, "Common/MatDefs/Misc/Sky.j3md");
|
Material skyMat = new Material(assetManager, "Common/MatDefs/Misc/Sky.j3md");
|
||||||
|
|
||||||
skyMat.setVector3("NormalScale", normalScale);
|
skyMat.setVector3("NormalScale", normalScale);
|
||||||
if (sphereMap){
|
if (sphereMap) {
|
||||||
skyMat.setBoolean("SphereMap", sphereMap);
|
skyMat.setBoolean("SphereMap", sphereMap);
|
||||||
}else if (!(texture instanceof TextureCubeMap)){
|
} else if (!(texture instanceof TextureCubeMap)) {
|
||||||
// make sure its a cubemap
|
// make sure its a cubemap
|
||||||
Image img = texture.getImage();
|
Image img = texture.getImage();
|
||||||
texture = new TextureCubeMap();
|
texture = new TextureCubeMap();
|
||||||
@ -43,23 +89,27 @@ public class SkyFactory {
|
|||||||
}
|
}
|
||||||
skyMat.setTexture("Texture", texture);
|
skyMat.setTexture("Texture", texture);
|
||||||
sky.setMaterial(skyMat);
|
sky.setMaterial(skyMat);
|
||||||
|
|
||||||
return sky;
|
return sky;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void checkImage(Image image){
|
private static void checkImage(Image image) {
|
||||||
// if (image.getDepth() != 1)
|
// if (image.getDepth() != 1)
|
||||||
// throw new IllegalArgumentException("3D/Array images not allowed");
|
// throw new IllegalArgumentException("3D/Array images not allowed");
|
||||||
|
|
||||||
if (image.getWidth() != image.getHeight())
|
if (image.getWidth() != image.getHeight()) {
|
||||||
throw new IllegalArgumentException("Image width and height must be the same");
|
throw new IllegalArgumentException("Image width and height must be the same");
|
||||||
|
}
|
||||||
|
|
||||||
if (image.getMultiSamples() != 1)
|
if (image.getMultiSamples() != 1) {
|
||||||
throw new IllegalArgumentException("Multisample textures not allowed");
|
throw new IllegalArgumentException("Multisample textures not allowed");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void checkImagesForCubeMap(Image ... images){
|
private static void checkImagesForCubeMap(Image... images) {
|
||||||
if (images.length == 1) return;
|
if (images.length == 1) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
Format fmt = images[0].getFormat();
|
Format fmt = images[0].getFormat();
|
||||||
int width = images[0].getWidth();
|
int width = images[0].getWidth();
|
||||||
@ -67,45 +117,63 @@ public class SkyFactory {
|
|||||||
|
|
||||||
checkImage(images[0]);
|
checkImage(images[0]);
|
||||||
|
|
||||||
for (int i = 1; i < images.length; i++){
|
for (int i = 1; i < images.length; i++) {
|
||||||
Image image = images[i];
|
Image image = images[i];
|
||||||
checkImage(images[i]);
|
checkImage(images[i]);
|
||||||
if (image.getFormat() != fmt) throw new IllegalArgumentException("Images must have same format");
|
if (image.getFormat() != fmt) {
|
||||||
if (image.getWidth() != width) throw new IllegalArgumentException("Images must have same resolution");
|
throw new IllegalArgumentException("Images must have same format");
|
||||||
if (image.getData(0).capacity() != size) throw new IllegalArgumentException("Images must have same size");
|
}
|
||||||
|
if (image.getWidth() != width) {
|
||||||
|
throw new IllegalArgumentException("Images must have same resolution");
|
||||||
|
}
|
||||||
|
if (image.getData(0).capacity() != size) {
|
||||||
|
throw new IllegalArgumentException("Images must have same size");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south, Texture up, Texture down, Vector3f normalScale){
|
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south, Texture up, Texture down, Vector3f normalScale) {
|
||||||
return createSky(assetManager, west, east, north, south, up, down, normalScale, 10);
|
return createSky(assetManager, west, east, north, south, up, down, normalScale, 10);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south, Texture up, Texture down, Vector3f normalScale, int sphereRadius){
|
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south, Texture up, Texture down, Vector3f normalScale, int sphereRadius) {
|
||||||
final Sphere sphereMesh = new Sphere(10, 10, sphereRadius, false, true);
|
final Sphere sphereMesh = new Sphere(10, 10, sphereRadius, false, true);
|
||||||
Geometry sky = new Geometry("Sky", sphereMesh);
|
Geometry sky = new Geometry("Sky", sphereMesh);
|
||||||
sky.setQueueBucket(Bucket.Sky);
|
sky.setQueueBucket(Bucket.Sky);
|
||||||
sky.setCullHint(Spatial.CullHint.Never);
|
sky.setCullHint(Spatial.CullHint.Never);
|
||||||
sky.setModelBound(new BoundingSphere(Float.POSITIVE_INFINITY, Vector3f.ZERO));
|
sky.setModelBound(new BoundingSphere(Float.POSITIVE_INFINITY, Vector3f.ZERO));
|
||||||
|
|
||||||
Image westImg = west.getImage();
|
Image westImg = west.getImage();
|
||||||
Image eastImg = east.getImage();
|
Image eastImg = east.getImage();
|
||||||
Image northImg = north.getImage();
|
Image northImg = north.getImage();
|
||||||
Image southImg = south.getImage();
|
Image southImg = south.getImage();
|
||||||
Image upImg = up.getImage();
|
Image upImg = up.getImage();
|
||||||
Image downImg = down.getImage();
|
Image downImg = down.getImage();
|
||||||
|
|
||||||
checkImagesForCubeMap(westImg, eastImg, northImg, southImg, upImg, downImg);
|
checkImagesForCubeMap(westImg, eastImg, northImg, southImg, upImg, downImg);
|
||||||
|
|
||||||
Image cubeImage = new Image(westImg.getFormat(), westImg.getWidth(), westImg.getHeight(), null);
|
Image cubeImage = new Image(westImg.getFormat(), westImg.getWidth(), westImg.getHeight(), null);
|
||||||
|
|
||||||
cubeImage.addData(westImg.getData(0));
|
cubeImage.addData(westImg.getData(0));
|
||||||
cubeImage.addData(eastImg.getData(0));
|
cubeImage.addData(eastImg.getData(0));
|
||||||
|
|
||||||
cubeImage.addData(downImg.getData(0));
|
cubeImage.addData(downImg.getData(0));
|
||||||
cubeImage.addData(upImg.getData(0));
|
cubeImage.addData(upImg.getData(0));
|
||||||
|
|
||||||
cubeImage.addData(southImg.getData(0));
|
cubeImage.addData(southImg.getData(0));
|
||||||
cubeImage.addData(northImg.getData(0));
|
cubeImage.addData(northImg.getData(0));
|
||||||
|
|
||||||
|
if (westImg.getEfficentData() != null){
|
||||||
|
// also consilidate efficient data
|
||||||
|
ArrayList<Object> efficientData = new ArrayList<Object>(6);
|
||||||
|
efficientData.add(westImg.getEfficentData());
|
||||||
|
efficientData.add(eastImg.getEfficentData());
|
||||||
|
efficientData.add(downImg.getEfficentData());
|
||||||
|
efficientData.add(upImg.getEfficentData());
|
||||||
|
efficientData.add(southImg.getEfficentData());
|
||||||
|
efficientData.add(northImg.getEfficentData());
|
||||||
|
cubeImage.setEfficentData(efficientData);
|
||||||
|
}
|
||||||
|
|
||||||
TextureCubeMap cubeMap = new TextureCubeMap(cubeImage);
|
TextureCubeMap cubeMap = new TextureCubeMap(cubeImage);
|
||||||
cubeMap.setAnisotropicFilter(0);
|
cubeMap.setAnisotropicFilter(0);
|
||||||
@ -121,22 +189,19 @@ public class SkyFactory {
|
|||||||
return sky;
|
return sky;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south, Texture up, Texture down){
|
public static Spatial createSky(AssetManager assetManager, Texture west, Texture east, Texture north, Texture south, Texture up, Texture down) {
|
||||||
return createSky(assetManager, west, east, north, south, up, down, Vector3f.UNIT_XYZ);
|
return createSky(assetManager, west, east, north, south, up, down, Vector3f.UNIT_XYZ);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, Texture texture, boolean sphereMap){
|
public static Spatial createSky(AssetManager assetManager, Texture texture, boolean sphereMap) {
|
||||||
return createSky(assetManager, texture, Vector3f.UNIT_XYZ, sphereMap);
|
return createSky(assetManager, texture, Vector3f.UNIT_XYZ, sphereMap);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Spatial createSky(AssetManager assetManager, String textureName, boolean sphereMap){
|
public static Spatial createSky(AssetManager assetManager, String textureName, boolean sphereMap) {
|
||||||
TextureKey key = new TextureKey(textureName, true);
|
TextureKey key = new TextureKey(textureName, true);
|
||||||
key.setGenerateMips(true);
|
key.setGenerateMips(true);
|
||||||
key.setAsCube(!sphereMap);
|
key.setAsCube(!sphereMap);
|
||||||
Texture tex = assetManager.loadTexture(key);
|
Texture tex = assetManager.loadTexture(key);
|
||||||
return createSky(assetManager, tex, sphereMap);
|
return createSky(assetManager, tex, sphereMap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -48,41 +48,6 @@ import javax.swing.SwingUtilities;
|
|||||||
|
|
||||||
public class JmeSystem {
|
public class JmeSystem {
|
||||||
|
|
||||||
public static enum Platform {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Microsoft Windows 32 bit
|
|
||||||
*/
|
|
||||||
Windows32,
|
|
||||||
/**
|
|
||||||
* Microsoft Windows 64 bit
|
|
||||||
*/
|
|
||||||
Windows64,
|
|
||||||
/**
|
|
||||||
* Linux 32 bit
|
|
||||||
*/
|
|
||||||
Linux32,
|
|
||||||
/**
|
|
||||||
* Linux 64 bit
|
|
||||||
*/
|
|
||||||
Linux64,
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 32 bit
|
|
||||||
*/
|
|
||||||
MacOSX32,
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 64 bit
|
|
||||||
*/
|
|
||||||
MacOSX64,
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 32 bit PowerPC
|
|
||||||
*/
|
|
||||||
MacOSX_PPC32,
|
|
||||||
/**
|
|
||||||
* Apple Mac OS X 64 bit PowerPC
|
|
||||||
*/
|
|
||||||
MacOSX_PPC64,
|
|
||||||
}
|
|
||||||
private static final Logger logger = Logger.getLogger(JmeSystem.class.getName());
|
private static final Logger logger = Logger.getLogger(JmeSystem.class.getName());
|
||||||
private static boolean initialized = false;
|
private static boolean initialized = false;
|
||||||
private static boolean lowPermissions = false;
|
private static boolean lowPermissions = false;
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user