diff --git a/src/de/phbouillon/android/framework/TimeFactorChangeListener.java b/src/de/phbouillon/android/framework/TimeFactorChangeListener.java index 5885d8a..a3907da 100644 --- a/src/de/phbouillon/android/framework/TimeFactorChangeListener.java +++ b/src/de/phbouillon/android/framework/TimeFactorChangeListener.java @@ -1,5 +1,5 @@ package de.phbouillon.android.framework; public interface TimeFactorChangeListener { - void timeFactorChanged(float oldTimeFactor, float newTimeFactor); + void timeFactorChanged(int oldTimeFactor, int newTimeFactor); } diff --git a/src/de/phbouillon/android/framework/impl/AndroidGame.java b/src/de/phbouillon/android/framework/impl/AndroidGame.java index bcb6a60..a243d25 100644 --- a/src/de/phbouillon/android/framework/impl/AndroidGame.java +++ b/src/de/phbouillon/android/framework/impl/AndroidGame.java @@ -2,7 +2,7 @@ /* Alite - Discover the Universe on your Favorite Android Device * Copyright (C) 2015 Philipp Bouillon - * + * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, version 3 of the License, or @@ -57,9 +57,9 @@ enum GLGameState { Finished, Idle } - + public static boolean resetting = false; - + private GLSurfaceView glView; private Graphics graphics; private Audio audio; @@ -74,7 +74,7 @@ enum GLGameState { private long startTime = System.nanoTime(); private long lastTime = startTime; private int frames = 0; - private float timeFactor = 1.0f; + private int timeFactor = 1; public static float fps; public static float scaleFactor; protected final TextureManager textureManager; @@ -87,14 +87,14 @@ public AndroidGame(int targetWidth, int targetHeight) { this.targetWidth = targetWidth; textureManager = new TextureManager(this); } - + public void setTimeFactorChangeListener(TimeFactorChangeListener tfl) { timeFactorChangeListener = tfl; } - + @Override public void onCreate(Bundle savedInstanceState) { - super.onCreate(savedInstanceState); + super.onCreate(savedInstanceState); requestWindowFeature(Window.FEATURE_NO_TITLE); getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN); @@ -102,10 +102,10 @@ public void onCreate(Bundle savedInstanceState) { getWindowManager().getDefaultDisplay().getMetrics(metrics); deviceWidth = metrics.widthPixels; - deviceHeight = metrics.heightPixels; + deviceHeight = metrics.heightPixels; glView = new GLSurfaceView(this); glView.setEGLConfigChooser(8, 8, 8, 8, 16, 0); - glView.setRenderer(AndroidGame.this); + glView.setRenderer(AndroidGame.this); if (fileIO == null) { fileIO = new AndroidFileIO(this); } @@ -120,37 +120,37 @@ public void onCreate(Bundle savedInstanceState) { input = new AndroidInput(this, glView, (float) frameBufferWidth / (float) aspect.width(), (float) frameBufferHeight / (float) aspect.height(), aspect.left, aspect.top); AliteLog.d("Calculating Sizes", "Sizes in OC: Width: " + deviceWidth + ", Height: " + deviceHeight + ", Aspect: " + aspect.left + ", " + aspect.top + ", " + aspect.right + ", " + aspect.bottom); } - + @Override public void onDestroy() { super.onDestroy(); } - + public int [] getSize() { if (sizeArray == null) { sizeArray = new int [] {deviceWidth, deviceHeight}; } return sizeArray; } - + @Override public void onResume() { super.onResume(); - if (glView != null) { + if (glView != null) { glView.onResume(); } if (screen != null) { screen.resume(); - } + } state = GLGameState.Running; } - + @Override public void onPause() { - super.onPause(); + super.onPause(); glView.onPause(); SoundManager.stopAll(); - if (screen != null) { + if (screen != null) { if (fatalException == null) { if (resetting) { resetting = false; @@ -161,21 +161,21 @@ public void onPause() { screen.pause(); } - fatalException = null; + fatalException = null; if (isFinishing()) { state = GLGameState.Finished; } else { state = GLGameState.Paused; - } + } if (isFinishing() && screen != null) { screen.dispose(); screen = null; } - + } - + protected abstract void saveState(); - + @Override public Input getInput() { return input; @@ -197,16 +197,16 @@ public Audio getAudio() { } @Override - public synchronized void setScreen(Screen screen) { + public synchronized void setScreen(Screen screen) { if (screen == null) { throw new IllegalArgumentException("Screen must not be null"); } - + this.screen.pause(); textureManager.clear(); - + this.screen = null; - screen.loadAssets(); + screen.loadAssets(); this.screen = screen; screen.activate(); screen.resume(); @@ -218,13 +218,13 @@ public synchronized void setScreen(Screen screen) { public Screen getCurrentScreen() { return screen; } - + public View getCurrentView() { return glView; } - + public Rect calculateTargetRect(Rect rect) { - int width = rect.right - rect.left; // "right" and "left" aren't named correctly here; right - left yields the width! + int width = rect.right - rect.left; // "right" and "left" aren't named correctly here; right - left yields the width! int height = rect.bottom - rect.top; // No adding of 1 required -- same is true for height... float xFactor = (float) targetWidth / (float) width; float yFactor = (float) targetHeight / (float) height; @@ -233,7 +233,7 @@ public Rect calculateTargetRect(Rect rect) { AliteLog.d("[ALITE-CTR]", "Width: " + width + ", Height: " + height); AliteLog.d("[ALITE-CTR]", "TargetWidth: " + targetWidth + ", targetHeight: " + targetHeight); AliteLog.d("[ALITE-CTR]", "Factors: " + xFactor + ", " + yFactor); - + int x1, y1, x2, y2; if (xFactor > yFactor) { x1 = rect.left; @@ -261,17 +261,17 @@ public void onSurfaceCreated(GL10 unused, EGLConfig config) { DisplayMetrics metrics = new DisplayMetrics(); getWindowManager().getDefaultDisplay().getMetrics(metrics); deviceWidth = metrics.widthPixels; - deviceHeight = metrics.heightPixels; + deviceHeight = metrics.heightPixels; Rect aspect = calculateTargetRect(new Rect(0, 0, deviceWidth, deviceHeight)); float ratio = (float) aspect.width() / (float) aspect.height(); GlUtils.setViewport(aspect); GlUtils.gluPerspective(this, 45.0f, ratio, 1.0f, 900000.0f); AliteLog.d("Recalculating Sizes", "Sizes in OSC: Width: " + deviceWidth + ", Height: " + deviceHeight + ", Aspect: " + aspect.left + ", " + aspect.top + ", " + aspect.right + ", " + aspect.bottom); - + GLES11.glEnable(GLES11.GL_TEXTURE_2D); graphics = new AndroidGraphics(fileIO, scaleFactor, aspect, textureManager); - + screen = getStartScreen(); // glView.onResume(); afterSurfaceCreated(); @@ -282,11 +282,11 @@ public void onSurfaceCreated(GL10 unused, EGLConfig config) { screen.resume(); startTime = System.nanoTime(); } - + @Override public void onSurfaceChanged(GL10 unused, int width, int height) { } - + private void drawFatalException() { try { if (fatalException != null) { @@ -299,14 +299,14 @@ private void drawFatalException() { throw new RuntimeException("Alite has ended with an uncaught exception while trying to process an uncaught exception.", t); } } - + @Override public void onDrawFrame(GL10 unused) { if (fatalException != null) { drawFatalException(); return; } - try { + try { GLGameState state = this.state; long nanoTime = System.nanoTime(); while ((nanoTime - startTime) < 33333333l) { @@ -354,18 +354,18 @@ public void onDrawFrame(GL10 unused) { public float getScaleFactor() { return scaleFactor; } - - public void afterSurfaceCreated() { - } - - public float getTimeFactor() { + + public void afterSurfaceCreated() { + } + + public int getTimeFactor() { return timeFactor; } - - public void setTimeFactor(float tf) { - if (timeFactorChangeListener != null && Math.abs(timeFactor - tf) > 0.0001f) { - timeFactorChangeListener.timeFactorChanged(timeFactor, tf); + + public void setTimeFactor(int tf) { + if ((timeFactorChangeListener != null) && (timeFactor != tf)) { + timeFactorChangeListener.timeFactorChanged(timeFactor, tf); } - timeFactor = tf; + timeFactor = tf; } } diff --git a/src/de/phbouillon/android/games/alite/model/Player.java b/src/de/phbouillon/android/games/alite/model/Player.java index d200544..8ed808d 100644 --- a/src/de/phbouillon/android/games/alite/model/Player.java +++ b/src/de/phbouillon/android/games/alite/model/Player.java @@ -121,7 +121,7 @@ public Condition getCondition() { public void setCondition(Condition newCondition) { condition = newCondition; if((condition != Condition.GREEN) && (condition != Condition.YELLOW)) - alite.setTimeFactor(1.0f); + alite.setTimeFactor(1); } public LegalStatus getLegalStatus() { diff --git a/src/de/phbouillon/android/games/alite/model/PlayerCobra.java b/src/de/phbouillon/android/games/alite/model/PlayerCobra.java index a7c7e7f..72ebc95 100644 --- a/src/de/phbouillon/android/games/alite/model/PlayerCobra.java +++ b/src/de/phbouillon/android/games/alite/model/PlayerCobra.java @@ -37,10 +37,10 @@ public class PlayerCobra { public static final int MAXIMUM_FUEL = 70; public static final int MAXIMUM_MISSILES = 4; public static final int DEFAULT_MISSILES = 3; + public static final int SPEED_UP_FACTOR = 10; // speed-up factor to use when torus can't be engaged public static final float MAX_SPEED = 367.4f; // m/s -- about 1320 km/h; just faster than sonic speed on Earth public static final float TORUS_SPEED = 33400.0f; // torus drive speed public static final float TORUS_TEST_SPEED = 10000.0f; // value to use to test if torus is engaged - public static final float SPEED_UP_FACTOR = 10.0f; // speed-up factor to use when torus can't be engaged public static final float MAX_SHIELD = 24; public static final float MAX_FUEL = 70; public static final float MAX_CABIN_TEMPERATURE = 30; diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/FlightScreen.java b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/FlightScreen.java index d983d0e..8064404 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/FlightScreen.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/FlightScreen.java @@ -476,9 +476,10 @@ public void performUpdate(float deltaTime) { if (isDisposed || inGame == null) { return; } - float dtf = deltaTime * ((Alite) game).getTimeFactor(); - inGame.performUpdate(dtf, allObjects); - + int tf = ((Alite) game).getTimeFactor(); + while((--tf >= 0) && inGame.isPlayerAlive()) { + inGame.performUpdate(deltaTime, allObjects); + } if (informationScreen != null) { informationScreen.update(deltaTime); } @@ -496,18 +497,19 @@ public void performUpdate(float deltaTime) { if (newScreen != null) { performScreenChange(newScreen); } else { + deltaTime *= ((Alite) game).getTimeFactor(); if (star != null) { - star.applyDeltaRotation(0.0f, (float) Math.toDegrees(0.02f * dtf), 0.0f); + star.applyDeltaRotation(0.0f, (float) Math.toDegrees(0.02f * deltaTime), 0.0f); } if (planet != null) { - planet.applyDeltaRotation(0.0f, (float) Math.toDegrees(0.015f * dtf), 0.0f); + planet.applyDeltaRotation(0.0f, (float) Math.toDegrees(0.015f * deltaTime), 0.0f); } if (spaceStation != null) { if (resetSpaceStation) { performResetSpaceStation(); } - spaceStation.applyDeltaRotation(0.0f, 0.0f, (float) Math.toDegrees(SPACE_STATION_ROTATION_SPEED * dtf)); + spaceStation.applyDeltaRotation(0.0f, 0.0f, (float) Math.toDegrees(SPACE_STATION_ROTATION_SPEED * deltaTime)); } } } catch (NullPointerException e) { diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/InGameHelper.java b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/InGameHelper.java index 92f7055..24c93f7 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/InGameHelper.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/InGameHelper.java @@ -103,7 +103,7 @@ void checkShipStationProximity() { return; } float distanceSq = ship.getPosition().distanceSq(station.getPosition()); - if (distanceSq <= STATION_PROXIMITY_DISTANCE_SQ * alite.getTimeFactor() * alite.getTimeFactor()) { + if (distanceSq <= STATION_PROXIMITY_DISTANCE_SQ) { if (ship.getProximity() != station) { ship.setProximity(station); AliteLog.e("Proximity", "Setting ship/station proximity"); @@ -125,7 +125,7 @@ void checkProximity(List allObjects) { continue; } SpaceObject objectA = (SpaceObject) allObjects.get(i); - float objectAProximityDistance = objectA.getBoundingSphereRadiusSq() * PROXIMITY_WARNING_RADIUS_FACTOR * alite.getTimeFactor(); + float objectAProximityDistance = objectA.getBoundingSphereRadiusSq() * PROXIMITY_WARNING_RADIUS_FACTOR; float distanceCamSq = objectA.getPosition().distanceSq(inGame.getShip().getPosition()); if (distanceCamSq <= objectAProximityDistance) { objectA.setProximity(inGame.getShip()); @@ -136,7 +136,7 @@ void checkProximity(List allObjects) { } SpaceObject objectB = (SpaceObject) allObjects.get(j); float distanceSq = objectA.getPosition().distanceSq(objectB.getPosition()); - float objectBProximityDistance = objectB.getBoundingSphereRadiusSq() * PROXIMITY_WARNING_RADIUS_FACTOR * alite.getTimeFactor(); + float objectBProximityDistance = objectB.getBoundingSphereRadiusSq() * PROXIMITY_WARNING_RADIUS_FACTOR; if (distanceSq <= objectAProximityDistance + objectBProximityDistance) { objectA.setProximity(objectB); objectB.setProximity(objectA); diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/LaserManager.java b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/LaserManager.java index 73dff7c..240b033 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/LaserManager.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/LaserManager.java @@ -689,7 +689,7 @@ final List registerTimedEvents() { @Override public void doPerform() { - long nd = ((alite.getCobra().isEquipmentInstalled(EquipmentStore.navalEnergyUnit)) ? NAVAL_REFRESH_RATE:NORMAL_REFRESH_RATE) / ((long) alite.getTimeFactor()); + long nd = ((alite.getCobra().isEquipmentInstalled(EquipmentStore.navalEnergyUnit)) ? NAVAL_REFRESH_RATE:NORMAL_REFRESH_RATE) / alite.getTimeFactor(); if (delay != nd) { updateDelay(nd); } diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/ObjectSpawnManager.java b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/ObjectSpawnManager.java index e2cc9e6..6c90ddb 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/ingame/ObjectSpawnManager.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/ingame/ObjectSpawnManager.java @@ -301,8 +301,8 @@ public void execute(float deltaTime) { } alite.setTimeFactorChangeListener(new TimeFactorChangeListener() { @Override - public void timeFactorChanged(float oldTimeFactor, float newTimeFactor) { - updateTimers(oldTimeFactor / newTimeFactor); + public void timeFactorChanged(int oldTimeFactor, int newTimeFactor) { + updateTimers(((float) oldTimeFactor) / ((float) newTimeFactor)); } }); } @@ -658,7 +658,7 @@ public void onUpdate(float deltaTime) { } private void spawnTrader() { - traderTimer.event.updateDelay((long) ((((600.0f + 300.0f * Math.random()) / 16.7f) * 1000000000l) / alite.getTimeFactor())); + traderTimer.event.updateDelay((long) ((((600.0f + 300.0f * Math.random()) / 16.7f) * 1000000000l) / ((float) alite.getTimeFactor()))); if (inGame.getWitchSpace() != null) { return; } @@ -748,7 +748,7 @@ public void onUpdate(float deltaTime) { } private void spawnAsteroid() { - asteroidTimer.event.updateDelay((long) ((((600.0f + 300.0f * Math.random()) / 16.7f) * 1000000000l) / alite.getTimeFactor())); + asteroidTimer.event.updateDelay((long) ((((600.0f + 300.0f * Math.random()) / 16.7f) * 1000000000l) / ((float) alite.getTimeFactor()))); if (inGame.getWitchSpace() != null) { return; } @@ -799,7 +799,7 @@ public void onUpdate(float deltaTime) { } private void spawnShuttleOrTransporter() { - shuttleOrTransportTimer.event.updateDelay((long) ((((600.0f + 300.0f * Math.random()) / 16.7f) * 1000000000l) / alite.getTimeFactor())); + shuttleOrTransportTimer.event.updateDelay((long) ((((600.0f + 300.0f * Math.random()) / 16.7f) * 1000000000l) / ((float) alite.getTimeFactor()))); if (inGame.getWitchSpace() != null || !inGame.isInSafeZone()) { return; } diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObject.java b/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObject.java index 6a512fe..26c2599 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObject.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObject.java @@ -2,7 +2,7 @@ /* Alite - Discover the Universe on your Favorite Android Device * Copyright (C) 2015 Philipp Bouillon - * + * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, version 3 of the License, or @@ -85,8 +85,8 @@ public abstract class SpaceObject extends AliteObject implements Geometry, Seria protected transient FloatBuffer texCoordBuffer; protected transient Alite alite; - - protected int numberOfVertices; + + protected int numberOfVertices; protected String textureFilename; protected final float [] displayMatrix = new float[16]; protected float [] boundingBox; @@ -106,7 +106,7 @@ public abstract class SpaceObject extends AliteObject implements Geometry, Seria protected int bounty; protected int score; protected int legalityType; - protected int maxCargoCanisters; + protected int maxCargoCanisters; protected boolean affectedByEnergyBomb = true; protected boolean inBay = false; protected ShipType shipType; @@ -121,54 +121,54 @@ public abstract class SpaceObject extends AliteObject implements Geometry, Seria protected String laserTexture = "textures/laser_orange.png"; protected transient List exhaust = new ArrayList(); protected boolean identified = false; - + private final List objectsToSpawn = new ArrayList(); - - + + private final static String [] matrixString = new String[] {"", "", "", ""}; private final SpaceObjectAI ai = new SpaceObjectAI(this); private ObjectType type; protected TargetBoxSpaceObject targetBox; - + protected SpaceObject proximity; - + public SpaceObject(Alite alite, String name, ObjectType type) { super(name); this.alite = alite; this.spawnCargoCanisters = true; - this.type = type; + this.type = type; } - + protected abstract void init(); - + protected void initTargetBox() { float size = getMaxExtentWithoutExhaust() * 1.25f; targetBox = new TargetBoxSpaceObject(alite, "targetBox", size, size, size); getHudColor().copy(v0); targetBox.setColor(v0.x, v0.y, v0.z); } - + public void addExhaust(EngineExhaust exhaust) { if (this.exhaust == null) { this.exhaust = new ArrayList(); } this.exhaust.add(exhaust); } - + public boolean isAffectedByEnergyBomb() { return affectedByEnergyBomb; } - + public List getExhausts() { return exhaust == null ? Collections. emptyList() : exhaust; } - + private void readObject(ObjectInputStream in) throws IOException { try { AliteLog.e("readObject", "SpaceObject.readObject"); in.defaultReadObject(); AliteLog.e("readObject", "SpaceObject.readObject I"); - this.alite = Alite.get(); + this.alite = Alite.get(); exhaust = new ArrayList(); init(); AliteLog.e("readObject", "SpaceObject.readObject II"); @@ -180,39 +180,39 @@ private void readObject(ObjectInputStream in) throws IOException { Alite getGame() { return alite; } - + public void setAggression(int aggression) { this.aggressionLevel = aggression; } - + public void addObjectToSpawn(ShipType type) { objectsToSpawn.add(type); } - + public List getObjectsToSpawn() { return objectsToSpawn; } - + public void clearObjectsToSpawn() { objectsToSpawn.clear(); } - + public ObjectType getType() { return type; } - + public void setType(ObjectType type) { this.type = type; } - + public final int getMissileCount() { return missileCount; } - + public final void setMissileCount(int newMissileCount) { missileCount = newMissileCount; } - + public boolean canFireMissile() { if (missileCount <= 0) { return false; @@ -220,23 +220,23 @@ public boolean canFireMissile() { if (lastMissileTime == -1 || (System.nanoTime() - lastMissileTime) > 4000000000l) { lastMissileTime = System.nanoTime(); return true; - } + } return false; } - + public void setEjected(boolean b) { this.ejected = b; } - + public boolean hasEjected() { return ejected; } - + public float getBoundingSphereRadius() { float me = getMaxExtent() / 2.0f; return (float) Math.sqrt(me * me * 3); } - + public float getBoundingSphereRadiusSq() { float me = getMaxExtent() / 2.0f; return me * me * 3.0f; @@ -245,11 +245,11 @@ public float getBoundingSphereRadiusSq() { public void setInBay(boolean b) { inBay = b; } - + public boolean isInBay() { return inBay; } - + public void setCloaked(boolean cloaked) { this.cloaked = cloaked; } @@ -257,12 +257,12 @@ public void setCloaked(boolean cloaked) { public boolean isCloaked() { return cloaked; } - + public String getDisplayMatrixString() { return String.format(Locale.getDefault(), "[%4.2f, %4.2f, %4.2f, %4.2f\n" + " %4.2f, %4.2f, %4.2f, %4.2f\n" + " %4.2f, %4.2f, %4.2f, %4.2f\n" + - " %4.2f, %4.2f, %4.2f, %4.2f]", + " %4.2f, %4.2f, %4.2f, %4.2f]", displayMatrix[ 0], displayMatrix[ 4], displayMatrix[ 8], displayMatrix[12], displayMatrix[ 1], displayMatrix[ 5], displayMatrix[ 9], displayMatrix[13], displayMatrix[ 2], displayMatrix[ 6], displayMatrix[10], displayMatrix[14], @@ -272,10 +272,10 @@ public String getDisplayMatrixString() { protected boolean receivesProximityWarning() { return true; } - - public void hasBeenHitByPlayer() { + + public void hasBeenHitByPlayer() { } - + public void setProximity(SpaceObject other) { if (other == null) { proximity = null; @@ -302,7 +302,7 @@ public void setProximity(SpaceObject other) { return; } } - + other.getPosition().sub(getPosition(), v0); float dotForward = v0.dot(getForwardVector()); float dotUp = v0.dot(getUpVector()); @@ -313,43 +313,95 @@ public void setProximity(SpaceObject other) { float dotSq = dotForward * dotForward + dotUp * dotUp + dotRight * dotRight; float collisionSq = getBoundingSphereRadius() * 3.0f + other.getBoundingSphereRadius() * 3.0f; collisionSq *= collisionSq; - + if (dotSq > collisionSq) { return; } - if (ai.getState() == AIState.EVADE) { - if (proximity != null && proximity != other) { - getPosition().sub(proximity.getPosition(), v0); - v0.normalize(); - float angleProx = getForwardVector().angleInDegrees(v0); - if (angleProx >= 180) { - angleProx = 360 - angleProx; - } - getPosition().sub(other.getPosition(), v0); - v0.normalize(); - float angleOther = getForwardVector().angleInDegrees(v0); - if (angleOther >= 180) { - angleOther = 360 - angleOther; - } - if (angleProx < angleOther) { - return; - } + if ((ai.getState() == AIState.EVADE) && (proximity != null)) { + getPosition().sub(proximity.getPosition(), v0); + v0.normalize(); + float angleProx = getForwardVector().angleInDegrees(v0); + if (angleProx >= 180) { + angleProx = 360 - angleProx; + } + getPosition().sub(other.getPosition(), v0); + v0.normalize(); + float angleOther = getForwardVector().angleInDegrees(v0); + if (angleOther >= 180) { + angleOther = 360 - angleOther; + } + if (angleProx < angleOther) { + return; } } + if (this instanceof CobraMkIII && ((CobraMkIII) this).isPlayerCobra()) { + Vector3f pP = new Vector3f(0, 0, 0); + Vector3f pvX = new Vector3f(0, 0, 0); + Vector3f pvY = new Vector3f(0, 0, 0); + Vector3f pvZ = new Vector3f(0, 0, 0); + Vector3f oP = new Vector3f(0, 0, 0); + Vector3f ovX = new Vector3f(0, 0, 0); + Vector3f ovY = new Vector3f(0, 0, 0); + Vector3f ovZ = new Vector3f(0, 0, 0); + Vector3f tt = new Vector3f(0, 0, 0); + getRightVector().copy(pvX); + pvX.scale(0.0f-boundingBox[0]); + getUpVector().copy(pvY); + pvY.scale(0.0f-boundingBox[2]); + getForwardVector().copy(pvZ); + pvZ.scale(boundingBox[4]); + getPosition().sub(pvX,pP); + pP.sub(pvY); + pP.sub(pvZ); + getRightVector().copy(tt); + tt.scale(boundingBox[1]); + pvX.add(tt); + getUpVector().copy(tt); + tt.scale(boundingBox[3]); + pvY.add(tt); + getForwardVector().copy(tt); + tt.scale(0.0f-boundingBox[5]); + pvZ.add(tt); + other.getRightVector().copy(ovX); + ovX.scale(0.0f-other.boundingBox[0]); + other.getUpVector().copy(ovY); + ovY.scale(0.0f-other.boundingBox[2]); + other.getForwardVector().copy(ovZ); + ovZ.scale(other.boundingBox[4]); + other.getPosition().sub(ovX,oP); + oP.sub(ovY); + oP.sub(ovZ); + other.getRightVector().copy(tt); + tt.scale(other.boundingBox[1]); + ovX.add(tt); + other.getUpVector().copy(tt); + tt.scale(other.boundingBox[3]); + ovY.add(tt); + other.getForwardVector().copy(tt); + tt.scale(0.0f-other.boundingBox[5]); + ovZ.add(tt); + AliteLog.e("AIS", + "PRXMTY: Player (" + getPosition().x + ":" + getPosition().y + ":" + getPosition().z + ":" + getBoundingSphereRadius() + + ":" + pP.x + ":" + pP.y + ":" + pP.z + ":" + pvX.x + ":" + pvX.y + ":" + pvX.z + ":" + pvY.x + ":" + pvY.y + ":" + pvY.z + ":" + pvZ.x + ":" + pvZ.y + ":" + pvZ.z + + ") " + other + + " (" + other.getPosition().x + ":" + other.getPosition().y + ":" + other.getPosition().z + ":" + other.getBoundingSphereRadius() + + ":" + oP.x + ":" + oP.y + ":" + oP.z + ":" + ovX.x + ":" + ovX.y + ":" + ovX.z + ":" + ovY.x + ":" + ovY.y + ":" + ovY.z + ":" + ovZ.x + ":" + ovZ.y + ":" + ovZ.z + + ")"); + } proximity = other; - } - + } + public SpaceObject getProximity() { return proximity; } - + @Override - public void render() { + public void render() { alite.getTextureManager().setTexture(textureFilename); GLES11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); GLES11.glVertexPointer(3, GLES11.GL_FLOAT, 0, vertexBuffer); GLES11.glNormalPointer(GLES11.GL_FLOAT, 0, normalBuffer); - GLES11.glTexCoordPointer(2, GLES11.GL_FLOAT, 0, texCoordBuffer); + GLES11.glTexCoordPointer(2, GLES11.GL_FLOAT, 0, texCoordBuffer); GLES11.glDrawArrays(GLES11.GL_TRIANGLES, 0, numberOfVertices); alite.getTextureManager().setTexture(null); if (Settings.engineExhaust && exhaust != null && !exhaust.isEmpty() && getSpeed() < 0f) { @@ -358,7 +410,7 @@ public void render() { } } } - + public void renderTargetBox(float distSq) { if (!Settings.targetBox || targetBox == null || distSq <= SpaceObjectAI.SHOOT_DISTANCE_SQ) { return; @@ -366,131 +418,131 @@ public void renderTargetBox(float distSq) { float alpha = (distSq - SpaceObjectAI.SHOOT_DISTANCE_SQ) / (LaserManager.MAX_ENEMY_DISTANCE_SQ - SpaceObjectAI.SHOOT_DISTANCE_SQ); targetBox.setAlpha(alpha); GLES11.glEnable(GLES11.GL_BLEND); - GLES11.glBlendFunc(GLES11.GL_SRC_ALPHA, GLES11.GL_ONE); + GLES11.glBlendFunc(GLES11.GL_SRC_ALPHA, GLES11.GL_ONE); targetBox.render(); GLES11.glDisable(GLES11.GL_BLEND); } @Override - public void setDisplayMatrix(float [] matrix) { + public void setDisplayMatrix(float [] matrix) { int counter = 0; for (float f: matrix) { displayMatrix[counter++] = f; } } - + @Override public float [] getDisplayMatrix() { return displayMatrix; } - + protected final FloatBuffer createFaces(float [] vertexData, float [] normalData, int ...indices) { vertices = new float[indices.length * 3]; normals = new float[indices.length * 3]; - + int offset = 0; for (int i: indices) { - vertices[offset] = vertexData[i * 3]; - vertices[offset + 1] = vertexData[i * 3 + 1]; - vertices[offset + 2] = -vertexData[i * 3 + 2]; - + vertices[offset] = vertexData[i * 3]; + vertices[offset + 1] = vertexData[i * 3 + 1]; + vertices[offset + 2] = -vertexData[i * 3 + 2]; + normals[offset] = -normalData[i * 3]; normals[offset + 1] = -normalData[i * 3 + 1]; - normals[offset + 2] = normalData[i * 3 + 2]; + normals[offset + 2] = normalData[i * 3 + 2]; offset += 3; } normalBuffer = GlUtils.toFloatBufferPositionZero(normals); - + return GlUtils.toFloatBufferPositionZero(vertices); } - + protected final FloatBuffer createScaledFaces(float scale, float [] vertexData, float [] normalData, int ...indices) { vertices = new float[indices.length * 3]; normals = new float[indices.length * 3]; - + int offset = 0; for (int i: indices) { - vertices[offset] = vertexData[i * 3] * scale; - vertices[offset + 1] = vertexData[i * 3 + 1] * scale; + vertices[offset] = vertexData[i * 3] * scale; + vertices[offset + 1] = vertexData[i * 3 + 1] * scale; vertices[offset + 2] = -vertexData[i * 3 + 2] * scale; - - normals[offset] = -normalData[i * 3]; + + normals[offset] = -normalData[i * 3]; normals[offset + 1] = -normalData[i * 3 + 1]; - normals[offset + 2] = normalData[i * 3 + 2]; + normals[offset + 2] = normalData[i * 3 + 2]; offset += 3; } normalBuffer = GlUtils.toFloatBufferPositionZero(normals); - + return GlUtils.toFloatBufferPositionZero(vertices); } protected final FloatBuffer createReversedFaces(float [] vertexData, float [] normalData, int ...indices) { vertices = new float[indices.length * 3]; normals = new float[indices.length * 3]; - + int offset = 0; for (int i: indices) { - vertices[offset] = vertexData[i * 3]; - vertices[offset + 1] = vertexData[i * 3 + 1]; - vertices[offset + 2] = vertexData[i * 3 + 2]; - - normals[offset] = -normalData[i * 3]; + vertices[offset] = vertexData[i * 3]; + vertices[offset + 1] = vertexData[i * 3 + 1]; + vertices[offset + 2] = vertexData[i * 3 + 2]; + + normals[offset] = -normalData[i * 3]; normals[offset + 1] = -normalData[i * 3 + 1]; - normals[offset + 2] = -normalData[i * 3 + 2]; + normals[offset + 2] = -normalData[i * 3 + 2]; offset += 3; } normalBuffer = GlUtils.toFloatBufferPositionZero(normals); - + return GlUtils.toFloatBufferPositionZero(vertices); } - + protected final FloatBuffer createReversedRotatedFaces(float [] vertexData, float [] normalData, int ...indices) { vertices = new float[indices.length * 3]; normals = new float[indices.length * 3]; - + int offset = 0; for (int i: indices) { - vertices[offset] = -vertexData[i * 3]; - vertices[offset + 1] = vertexData[i * 3 + 1]; - vertices[offset + 2] = -vertexData[i * 3 + 2]; - + vertices[offset] = -vertexData[i * 3]; + vertices[offset + 1] = vertexData[i * 3 + 1]; + vertices[offset + 2] = -vertexData[i * 3 + 2]; + normals[offset] = normalData[i * 3]; normals[offset + 1] = -normalData[i * 3 + 1]; - normals[offset + 2] = normalData[i * 3 + 2]; + normals[offset + 2] = normalData[i * 3 + 2]; offset += 3; } normalBuffer = GlUtils.toFloatBufferPositionZero(normals); - + return GlUtils.toFloatBufferPositionZero(vertices); } - + // -1 0 0 // 0 1 0 // 0 0 -1 protected final FloatBuffer createReversedScaledFaces(float scale, float [] vertexData, float [] normalData, int ...indices) { vertices = new float[indices.length * 3]; normals = new float[indices.length * 3]; - + int offset = 0; for (int i: indices) { - vertices[offset] = vertexData[i * 3] * scale; - vertices[offset + 1] = vertexData[i * 3 + 1] * scale; - vertices[offset + 2] = vertexData[i * 3 + 2] * scale; - - normals[offset] = -normalData[i * 3]; - normals[offset + 1] = -normalData[i * 3 + 1]; - normals[offset + 2] = -normalData[i * 3 + 2]; + vertices[offset] = vertexData[i * 3] * scale; + vertices[offset + 1] = vertexData[i * 3 + 1] * scale; + vertices[offset + 2] = vertexData[i * 3 + 2] * scale; + + normals[offset] = -normalData[i * 3]; + normals[offset + 1] = -normalData[i * 3 + 1]; + normals[offset + 2] = -normalData[i * 3 + 2]; offset += 3; } normalBuffer = GlUtils.toFloatBufferPositionZero(normals); - + return GlUtils.toFloatBufferPositionZero(vertices); } - + public float [] getBoundingBox() { return boundingBox; } - + public void scaleBoundingBox(float scale) { if (originalBoundingBox == null) { originalBoundingBox = new float[boundingBox.length]; @@ -518,19 +570,19 @@ public float getMaxExtent() { } return Math.max(Math.abs(boundingBox[0]) + Math.abs(boundingBox[1]), Math.max(Math.abs(boundingBox[2]) + Math.abs(boundingBox[3]), - Math.abs(boundingBox[4]) + Math.abs(boundingBox[5]) + add)); + Math.abs(boundingBox[4]) + Math.abs(boundingBox[5]) + add)); } - + public float getMaxExtentWithoutExhaust() { return Math.max(Math.abs(boundingBox[0]) + Math.abs(boundingBox[1]), Math.max(Math.abs(boundingBox[2]) + Math.abs(boundingBox[3]), - Math.abs(boundingBox[4]) + Math.abs(boundingBox[5]))); + Math.abs(boundingBox[4]) + Math.abs(boundingBox[5]))); } public float getMedianRadius() { return (Math.abs(boundingBox[0]) + Math.abs(boundingBox[1]) + Math.abs(boundingBox[2]) + Math.abs(boundingBox[3]) + - Math.abs(boundingBox[4]) + Math.abs(boundingBox[5])) / 6.0f; + Math.abs(boundingBox[4]) + Math.abs(boundingBox[5])) / 6.0f; } public void dispose() { @@ -538,15 +590,15 @@ public void dispose() { alite.getTextureManager().freeTexture(textureFilename); } } - + public float getMaxSpeed() { return maxSpeed; } - + public float getMaxRollSpeed() { return maxRollSpeed; } - + public float getMaxPitchSpeed() { return maxPitchSpeed; } @@ -554,30 +606,30 @@ public float getMaxPitchSpeed() { public float getHullStrength() { return hullStrength; } - + public boolean hasEcm() { return hasEcm; } - + public int getAggressionLevel() { return aggressionLevel; } - + public boolean spawnsCargoCanisters() { return spawnCargoCanisters; } - + public int getMaxCargoCanisters() { return maxCargoCanisters; } - + public TradeGood getCargoType() { if (cargoType <= 0) { return null; } return TradeGoodStore.get().fromNumber(cargoType); } - + public float applyDamage(float amount) { hullStrength -= amount; if (hullStrength < 0) { @@ -585,7 +637,7 @@ public float applyDamage(float amount) { } return hullStrength; } - + public float setHullStrength(float newHullStrength) { hullStrength = newHullStrength; if (hullStrength < 0) { @@ -593,7 +645,7 @@ public float setHullStrength(float newHullStrength) { } return hullStrength; } - + public boolean intersect(Vector3f origin, Vector3f direction) { float [] verts = new float[vertices.length]; float [] matrix = getMatrix(); @@ -604,7 +656,7 @@ public boolean intersect(Vector3f origin, Vector3f direction) { } return intersectInternal(numberOfVertices, origin, direction, verts); } - + public boolean intersect(Vector3f origin, Vector3f direction, float scaleFactor) { float [] verts = new float[vertices.length]; float [] matrix = getMatrix(); @@ -615,18 +667,18 @@ public boolean intersect(Vector3f origin, Vector3f direction, float scaleFactor) } return intersectInternal(numberOfVertices, origin, direction, verts); } - + public static final String debugMatrix(float [] matrix, boolean cr) { matrixString[0] += String.format("[%+07.4f %+07.4f %+07.4f %+07.4f ", matrix[ 0], matrix[ 4], matrix[ 8], matrix[12]); matrixString[1] += String.format(" %+07.4f %+07.4f %+07.4f %+07.4f ", matrix[ 1], matrix[ 5], matrix[ 9], matrix[13]); matrixString[2] += String.format(" %+07.4f %+07.4f %+07.4f %+07.4f ", matrix[ 2], matrix[ 6], matrix[10], matrix[14]); matrixString[3] += String.format(" %+07.4f %+07.4f %+07.4f %+07.4f] ", matrix[ 3], matrix[ 7], matrix[11], matrix[15]); - if (cr) { + if (cr) { return matrixString[0] + "\n" + matrixString[1] + "\n" + matrixString[2] + "\n" + matrixString[3]; } return ""; } - + public void orientTowards(float x, float y, float z, float ux, float uy, float uz) { v0.x = x; v0.y = y; @@ -636,17 +688,17 @@ public void orientTowards(float x, float y, float z, float ux, float uy, float u v1.z = uz; ai.orient(v0, v1, 0); } - + public float orientTowards(GraphicObject object, float deltaTime) { object.getUpVector().copy(v0); // v0.negate(); return ai.orient(object.getPosition(), v0, deltaTime); } - + public float orientTowards(GraphicObject object, Vector3f up, float deltaTime) { return ai.orient(object.getPosition(), up, deltaTime); } - + public float orientTowardsUsingRollPitch(GraphicObject object, Vector3f up, float deltaTime) { return ai.orientUsingRollPitchOnly(object.getPosition(), up, deltaTime); } @@ -655,19 +707,19 @@ public void setRandomOrientation(Vector3f origin, Vector3f up) { up.copy(v0); v1.x = (float) (0.7 - Math.random() * 1.4); v1.y = (float) (0.7 - Math.random() * 1.4); - v1.z = (float) (0.7 - Math.random() * 1.4); + v1.z = (float) (0.7 - Math.random() * 1.4); MathHelper.getRandomPosition(origin, v1, 16384.0f, 8192.0f); ai.orient(v1, v0, 0); } - + final void updateInternals() { computeMatrix(); } - + final void computeInternals() { extractVectors(); } - + public void update(float deltaTime) { ai.update(deltaTime); if (Settings.engineExhaust && exhaust != null) { @@ -676,27 +728,27 @@ public void update(float deltaTime) { } } } - + public void setAIState(AIState newState, Object ...data) { ai.setState(newState, data); } - + public AIState getAIState() { return ai.getState(); } - + public String getCurrentAIStack() { return ai.getStateStack(); } - + public int getNumberOfLasers() { return laserHardpoints.size() / 3; } - + public float getLaserX(int i) { return laserHardpoints.get(i * 3); } - + public float getLaserY(int i) { return laserHardpoints.get(i * 3 + 1); } @@ -704,7 +756,7 @@ public float getLaserY(int i) { public float getLaserZ(int i) { return laserHardpoints.get(i * 3 + 2); } - + private static SpaceObject createGalaxyLocalShip(final Alite alite, int extraShip, int which) { // From the initial seed of galaxy 1, retain only the first four bits (0x5). // Now, if this is done for each of the "official" 8 galaxies, the galaxies 1-8 have those @@ -721,18 +773,18 @@ private static SpaceObject createGalaxyLocalShip(final Alite alite, int extraShi // 9 or 1: Additional ships for "Galaxy 7" (Dugite and Lyre) // 2 or 3: Additional ships for "Galaxy 8" (Harlequin and Rattlesnake) if (extraShip == 11 || extraShip == 12) { - return which == 0 ? new Cottonmouth(alite) : new Hognose2(alite); // Galaxy 2 + return which == 0 ? new Cottonmouth(alite) : new Hognose2(alite); // Galaxy 2 } if (extraShip == 6 || extraShip == 7) { return which == 0 ? new Boomslang(alite) : new Lora(alite); // Galaxy 3 } if (extraShip == 13 || extraShip == 14) { - return which == 0 ? new Gopher(alite) : new Mussurana(alite); // Galaxy 4 + return which == 0 ? new Gopher(alite) : new Mussurana(alite); // Galaxy 4 } - if (extraShip == 10 || extraShip == 15) { + if (extraShip == 10 || extraShip == 15) { return which == 0 ? new Bushmaster(alite) : new Indigo(alite); // Galaxy 5 } - if (extraShip == 4 || extraShip == 0) { + if (extraShip == 4 || extraShip == 0) { return which == 0 ? new Coral(alite) : new Yellowbelly(alite); // Galaxy 6 } if (extraShip == 9 || extraShip == 1) { @@ -772,7 +824,7 @@ public static SpaceObject createRandomEnemy(final Alite alite) { } return new Krait(alite); } - + public static SpaceObject createRandomTrader(final Alite alite) { int type = (int) (Math.random() * 5); switch (type) { @@ -805,66 +857,66 @@ public static SpaceObject createRandomAsteroid(final Alite alite) { } return new Asteroid1(alite); } - + public void aiStateCallback(AiStateCallback type) { AiStateCallbackHandler handler = aiStateCallbackHandlers.get(type); if (handler != null) { handler.execute(this); } } - + public void executeHit(SpaceObject player) { ai.executeHit(player); } - + public void registerAiStateCallbackHandler(AiStateCallback type, AiStateCallbackHandler handler) { aiStateCallbackHandlers.put(type, handler); } - + public void clearAiStateCallbackHandler(AiStateCallback type) { aiStateCallbackHandlers.remove(type); } - + public int getBounty() { return bounty; } - + public int getScore() { return score; } - + public ShipType getShipType() { return shipType; } - + public boolean avoidObstacles() { return true; } - + public String toString() { return getName(); } public int getCargoCanisterOverrideCount() { return cargoCanisterCount; - } - + } + public void setCargoCanisterCount(int count) { cargoCanisterCount = count; } - + public void setIgnoreSafeZone(boolean b) { ignoreSafeZone = true; } - + public boolean isIgnoreSafeZone() { return ignoreSafeZone; } - + public long getLaserColor() { return laserColor; } - + public String getLaserTexture() { return laserTexture; } @@ -872,7 +924,7 @@ public String getLaserTexture() { public boolean isIdentified() { return identified; } - + public void setIdentified() { identified = true; } diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObjectAI.java b/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObjectAI.java index b8d4afb..813e945 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObjectAI.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/objects/space/SpaceObjectAI.java @@ -2,7 +2,7 @@ /* Alite - Discover the Universe on your Favorite Android Device * Copyright (C) 2015 Philipp Bouillon - * + * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, version 3 of the License, or @@ -41,23 +41,23 @@ public final class SpaceObjectAI implements Serializable { private static final long serialVersionUID = 8646121427456794783L; - + private static final float MISSILE_MIN_DIST_SQ = 36000000.0f; public static final float SHOOT_DISTANCE_SQ = 81000000.0f; private static final float FIRE_MISSILE_UPON_FIRST_HIT_PROBABILITY = 5.0f; private static final long BASE_DELAY_BETWEEN_SHOOT_CHECKS = 59880239l; // 16.7 FPS - private static final long SHOOT_DELAY_REDUCE_PER_RATING_LEVEL = 3318363l; // 1.6625 Delta FPS + private static final long SHOOT_DELAY_REDUCE_PER_RATING_LEVEL = 3318363l; // 1.6625 Delta FPS // => ~30 FPS at Elite. private final SpaceObject so; - + private final Quaternion q1 = new Quaternion(); private final Quaternion q2 = new Quaternion(); private final Quaternion q3 = new Quaternion(); private final Vector3f v0 = new Vector3f(0, 0, 0); private final Vector3f v1 = new Vector3f(0, 0, 0); - private final Vector3f v2 = new Vector3f(0, 0, 0); + private final Vector3f v2 = new Vector3f(0, 0, 0); private final Vector3f v3 = new Vector3f(0, 0, 0); - + private Stack currentState = new Stack(); private GraphicObject target = null; private Vector3f evadePosition = new Vector3f(0, 0, 0); @@ -72,36 +72,36 @@ public final class SpaceObjectAI implements Serializable { private Curve curve = null; private long curveFollowStart; private final Vector3f lastRotation = new Vector3f(0, 0, 0); - + public SpaceObjectAI(final SpaceObject so) { this.so = so; currentState.push(AIState.IDLE); } - + public float orientUsingRollPitchOnly(Vector3f targetPosition, Vector3f targetUp, float deltaTime) { float result = trackInternal(targetPosition, targetUp, 1000.0f, deltaTime, false); executeSteeringNoSpeedChange(targetPosition); return result; } - + private float trackPosition(Vector3f targetPosition, Vector3f targetUp, float deltaTime) { so.updateInternals(); - Quaternion.fromMatrix(so.getMatrix(), q1); + Quaternion.fromMatrix(so.getMatrix(), q1); q1.normalize(); - - so.getPosition().sub(targetPosition, v0); + + so.getPosition().sub(targetPosition, v0); v0.normalize(); - + targetUp.cross(v0, v1); v1.normalize(); v0.cross(v1, v2); v2.normalize(); - + Quaternion.fromVectors(v1, v2, v0, q2); - q2.normalize(); + q2.normalize(); q1.computeDifference(q2, q3); q3.normalize(); - + q3.axisOfRotation(v0); float angle = (float) Math.toDegrees(q3.angleOfRotation()); if (angle > 180) { @@ -115,11 +115,11 @@ private float trackPosition(Vector3f targetPosition, Vector3f targetUp, float de if (Math.abs(angle) > 0.0001f && !Float.isInfinite(angle) && !Float.isNaN(angle)) { Matrix.rotateM(so.getMatrix(), 0, angle, v0.x, v0.y, v0.z); so.computeInternals(); - } - - return absAngle; + } + + return absAngle; } - + private float trackInternal(Vector3f targetPosition, Vector3f targetUp, float desiredRangeSq, float deltaTime, boolean retreat) { float rate1 = 2.0f * deltaTime; float rate2 = 4.0f * deltaTime; @@ -128,14 +128,14 @@ private float trackInternal(Vector3f targetPosition, Vector3f targetUp, float de float reverse = 1.0f; float minD = 0.004f; float maxCos = 0.995f; - + float maxPitch = so.getMaxPitchSpeed() * 30 * deltaTime; float maxRoll = so.getMaxRollSpeed() * 30 * deltaTime; - + if (retreat) { reverse = -reverse; } - + so.getPosition().sub(targetPosition, v0); float rangeSq = v0.lengthSq(); if (rangeSq > desiredRangeSq) { @@ -146,22 +146,21 @@ private float trackInternal(Vector3f targetPosition, Vector3f targetUp, float de } else { v0.normalize(); } - + float dRight = v0.dot(so.getRightVector()); float dUp = v0.dot(so.getUpVector()); float dForward = v0.dot(so.getForwardVector()); - + if (pitchingOver) { maxPitch *= 4.0f; maxRoll *= 4.0f; if (reverse * dUp < 0) { stickPitch = maxPitch; } else { - stickPitch = -maxPitch; + stickPitch = -maxPitch; } pitchingOver = reverse * dForward < 0.707; } - if (dForward < maxCos || retreat) { if (dForward <= -maxCos) { dUp = minD * 2.0f; @@ -178,7 +177,7 @@ private float trackInternal(Vector3f targetPosition, Vector3f targetUp, float de stickRoll = maxRoll * 0.125f * factor; } if (Math.abs(dRight) < Math.abs(stickRoll) * deltaTime) { - stickRoll = Math.abs(dRight) * Alite.get().getTimeFactor() / deltaTime * (stickRoll < 0 ? -1 : 1); + stickRoll = Math.abs(dRight) / deltaTime * (stickRoll < 0 ? -1 : 1); } } if (dUp < -minD) { @@ -193,7 +192,7 @@ private float trackInternal(Vector3f targetPosition, Vector3f targetUp, float de stickRoll = -maxRoll * 0.125f * factor; } if (Math.abs(dRight) < Math.abs(stickRoll) * deltaTime) { - stickRoll = Math.abs(dRight) * Alite.get().getTimeFactor() / deltaTime * (stickRoll < 0 ? -1 : 1); + stickRoll = Math.abs(dRight) / deltaTime * (stickRoll < 0 ? -1 : 1); } } if (Math.abs(stickRoll) < 0.0001) { @@ -208,54 +207,52 @@ private float trackInternal(Vector3f targetPosition, Vector3f targetUp, float de stickPitch = maxPitch * reverse * 0.125f * factor; } if (Math.abs(dUp) < Math.abs(stickPitch) * deltaTime) { - stickPitch = Math.abs(dUp) * Alite.get().getTimeFactor() / deltaTime * (stickPitch < 0 ? -1 : 1); + stickPitch = Math.abs(dUp) / deltaTime * (stickPitch < 0 ? -1 : 1); } } } - // if (targetUp != null) { // stickRoll = rollToMatchUp(targetUp); // } - + if ((stickRoll > 0.0 && flightRoll < 0.0) || (stickRoll < 0.0 && flightRoll > 0.0)) { rate1 *= 4.0f; } if ((stickPitch > 0.0 && flightPitch < 0.0) || (stickPitch < 0.0 && flightPitch > 0.0)) { rate2 *= 4.0f; } - + if (flightRoll < stickRoll - rate1) { stickRoll = flightRoll + rate1; } if (flightRoll > stickRoll + rate1) { stickRoll = flightRoll - rate1; } - if (flightPitch < stickPitch - rate2) { + if (flightPitch < stickPitch - rate2) { stickPitch = flightPitch + rate2; - } + } if (flightPitch > stickPitch + rate2) { stickPitch = flightPitch - rate2; } - + flightRoll = stickRoll; flightPitch = stickPitch; - - + + if (retreat) { dForward *= dForward; } - if (dForward < 0.0) { return 0.0f; } - + if (Math.abs(flightRoll) < 0.0001 && Math.abs(flightPitch) < 0.0001) { return 1.0f; } - - return dForward; + + return dForward; } - + private float executeSteering(float desiredSpeed) { so.applyDeltaRotation(flightPitch, 0, flightRoll); if (so instanceof CobraMkIII && ((CobraMkIII) so).isPlayerCobra()) { @@ -279,7 +276,7 @@ private float executeSteering(float desiredSpeed) { } return angle; } - + private float executeSteeringNoSpeedChange(Vector3f targetPosition) { so.applyDeltaRotation(flightPitch, 0, flightRoll); if (so instanceof CobraMkIII && ((CobraMkIII) so).isPlayerCobra()) { @@ -310,29 +307,29 @@ private float executeSteering(float desiredSpeed, Vector3f position) { } return angle; } - + private final float clamp(float val, float min, float max) { return val < min ? min : val > max ? max : val; } public float orient(Vector3f targetPosition, Vector3f targetUp, float deltaTime) { so.updateInternals(); - Quaternion.fromMatrix(so.getMatrix(), q1); + Quaternion.fromMatrix(so.getMatrix(), q1); q1.normalize(); - - so.getPosition().sub(targetPosition, v0); + + so.getPosition().sub(targetPosition, v0); v0.normalize(); - + targetUp.cross(v0, v1); v1.normalize(); v0.cross(v1, v2); v2.normalize(); - + Quaternion.fromVectors(v1, v2, v0, q2); - q2.normalize(); + q2.normalize(); q1.computeDifference(q2, q3); q3.normalize(); - + q3.axisOfRotation(v0); float angle = (float) Math.toDegrees(q3.angleOfRotation()); if (angle > 180) { @@ -357,10 +354,10 @@ public float orient(Vector3f targetPosition, Vector3f targetUp, float deltaTime) so.getGame().getCobra().setRotation(v0.dot(v1), v0.dot(v2)); } so.computeInternals(); - } + } return result; } - + private final void calculateTrackingSpeed(float angle) { if (so instanceof Missile) { if (angle > 50) { @@ -390,28 +387,28 @@ private final void calculateTrackingSpeed(float angle) { so.adjustSpeed(-so.getMaxSpeed() * 0.8f); } else { so.adjustSpeed(-so.getMaxSpeed()); - } + } } - + private void avoidCollision() { SpaceObject proximity = so.getProximity(); if (proximity != null && !so.inBay) { pushState(AIState.EVADE, proximity); } } - + private void attackObject(float deltaTime) { if (target instanceof CobraMkIII && ((CobraMkIII) target).isPlayerCobra()) { if (InGameManager.playerInSafeZone && !(so instanceof Viper) && !(so.isIgnoreSafeZone())) { waitForSafeZoneExit = true; pushState(AIState.FLEE, target); return; - } + } } trackInternal(target.getPosition(), null, 1000.0f, deltaTime, false); avoidCollision(); float angle = executeSteering(-1); - float distanceSq = so.getPosition().distanceSq(target.getPosition()); + float distanceSq = so.getPosition().distanceSq(target.getPosition()); if (angle < 10 && distanceSq < SHOOT_DISTANCE_SQ && !so.hasEjected()) { if (target instanceof SpaceObject && ((SpaceObject) target).isCloaked()) { return; @@ -426,39 +423,39 @@ private void attackObject(float deltaTime) { } } lastShootCheck = System.nanoTime(); - } + } } } - - private void fleeObject(float deltaTime) { + + private void fleeObject(float deltaTime) { if (target instanceof CobraMkIII && ((CobraMkIII) target).isPlayerCobra()) { if (!InGameManager.playerInSafeZone && waitForSafeZoneExit) { popState(); waitForSafeZoneExit = false; return; - } + } } trackInternal(target.getPosition(), null, 1000.0f, deltaTime, true); avoidCollision(); executeSteering(so.getMaxSpeed()); } - + private void flyStraight(float deltaTime) { avoidCollision(); } private void flyPath(float deltaTime) { - if (waypoints.isEmpty()) { + if (waypoints.isEmpty()) { popState(); if (currentState.isEmpty()) { setState(AIState.IDLE, (Object []) null); } so.aiStateCallback(AiStateCallback.EndOfWaypointsReached); return; - } + } WayPoint wp = waypoints.get(0); float d = trackInternal(wp.position, wp.upVector, 1000.0f, deltaTime, false); - float targetSpeed = wp.orientFirst ? 0.0f : so.getMaxSpeed(); + float targetSpeed = wp.orientFirst ? 0.0f : so.getMaxSpeed(); if (Math.abs(1.0 - d) < 0.01 && wp.orientFirst) { targetSpeed = so.getMaxSpeed(); wp.orientFirst = false; @@ -475,22 +472,22 @@ private void flyPath(float deltaTime) { currentDistance = distance; } } - + private void followCurve(float deltaTime) { float time = (System.nanoTime() - curveFollowStart) / 1000000000.0f; curve.compute(time); - - so.setPosition(curve.getCurvePosition()); + + so.setPosition(curve.getCurvePosition()); so.setForwardVector(curve.getcForward()); so.setRightVector(curve.getcRight()); so.setUpVector(curve.getcUp()); - + curve.getCurveRotation().copy(v0); so.applyDeltaRotation(v0.x, v0.y, v0.z); so.assertOrthoNormal(); - + // avoidCollision(); - + if (curve.reachedEnd()) { popState(); if (currentState.isEmpty()) { @@ -499,8 +496,8 @@ private void followCurve(float deltaTime) { } } } - - private void updateEvade(float deltaTime) { + + private void updateEvade(float deltaTime) { float distanceSq = so.getPosition().distanceSq(evadePosition); SpaceObject proximity = so.getProximity(); boolean clearEvade = false; @@ -515,17 +512,17 @@ private void updateEvade(float deltaTime) { if (currentState.isEmpty()) { setState(AIState.IDLE, (Object []) null); } - return; - } - so.getProximity().getPosition().sub(so.getPosition(), v0); + return; + } + proximity.getPosition().sub(so.getPosition(), v0); v0.scale(0.5f); v0.add(so.getPosition()); - v0.copy(evadePosition); - evadeRangeSq = (so.getProximity().getBoundingSphereRadiusSq() * 3.0f + so.getBoundingSphereRadiusSq() * 3.0f) * 18; + v0.copy(evadePosition); + evadeRangeSq = (proximity.getBoundingSphereRadiusSq() * 3.0f + so.getBoundingSphereRadiusSq() * 3.0f) * 18; float dForward = trackInternal(evadePosition, null, evadeRangeSq, deltaTime, true); executeSteering(so.getMaxSpeed() * (0.5f * dForward + 0.5f)); } - + private void updateTrack(float deltaTime) { if (so instanceof Missile && target != null) { float angle = trackPosition(target.getPosition(), target.getUpVector(), deltaTime); @@ -537,7 +534,7 @@ private void updateTrack(float deltaTime) { } executeSteering(so instanceof Missile ? -1 : so.getMaxSpeed()); } - + private void initiateTrack(boolean replace, Object [] data) { if (replace) { currentState.clear(); @@ -552,14 +549,14 @@ private void initiateMissileTrack(boolean replace, Object [] data) { if (replace) { currentState.clear(); } - target = data == null || data[0] == null ? null : (GraphicObject) data[0]; + target = data == null || data[0] == null ? null : (GraphicObject) data[0]; if (target != null) { float distanceSq = target.getPosition().distanceSq(so.getPosition()); if (distanceSq < 9000000) { currentState.push(AIState.TRACK); } else { pushState(AIState.TRACK, target); - so.getPosition().copy(v0); + so.getPosition().copy(v0); target.getPosition().sub(v0, v1); v1.scale(0.5f); target.getPosition().sub(v1, v0); @@ -571,7 +568,7 @@ private void initiateMissileTrack(boolean replace, Object [] data) { } } } - + private void initiateIdle(boolean replace, Object [] data) { if (replace) { currentState.clear(); @@ -596,10 +593,10 @@ private void initiateStraight(boolean replace, Object [] data) { so.setSpeed(-(Float) data[0]); } } else { - so.adjustSpeed(-so.getMaxSpeed()); - } + so.adjustSpeed(-so.getMaxSpeed()); + } } - + private void initiatePath(boolean replace, Object [] data) { if (replace) { currentState.clear(); @@ -632,7 +629,7 @@ private void initiateFollowCurve(boolean replace, Object [] data) { } waypoints.clear(); if (data != null && data.length > 0) { - curve = (Curve) data[0]; + curve = (Curve) data[0]; curveFollowStart = System.nanoTime(); } currentDistance = -1; @@ -655,21 +652,21 @@ private void initiateFlee(boolean replace, Object [] data) { private void getFartherDirection(Vector3f direction, final Vector3f targetVector, final float scale) { so.getPosition().sub(target.getPosition(), v0); v0.normalize(); - + direction.copy(targetVector); targetVector.scale(scale); - so.getPosition().add(targetVector, v2); + so.getPosition().add(targetVector, v2); float d1s = v2.distanceSq(target.getPosition()); - + targetVector.negate(); so.getPosition().add(targetVector, v2); float d2s = v2.distanceSq(target.getPosition()); - + if (d1s > d2s) { targetVector.negate(); } } - + private void initiateBank(boolean replace, Object [] data) { target = data == null || data[0] == null ? null : (GraphicObject) data[0]; if (target == null) { @@ -689,11 +686,11 @@ private void initiateBank(boolean replace, Object [] data) { v0.scale(10000.0f); v2.add(v0); WayPoint wp2 = WayPoint.newWayPoint(v2, target.getUpVector()); - + if (replace) { setState(AIState.FLY_PATH, wp1, wp2); } else { - pushState(AIState.FLY_PATH, wp1, wp2); + pushState(AIState.FLY_PATH, wp1, wp2); } } @@ -710,11 +707,11 @@ private void initiateEvade(boolean replace, Object [] data) { so.getProximity().getPosition().sub(so.getPosition(), v0); v0.scale(0.5f); v0.add(so.getPosition()); - v0.copy(evadePosition); + v0.copy(evadePosition); evadeRangeSq = (so.getProximity().getBoundingSphereRadiusSq() * 3.0f + so.getBoundingSphereRadiusSq() * 3.0f) * 18; pitchingOver = true; } - + private void initiateAttack(boolean replace, Object [] data) { if (replace) { currentState.clear(); @@ -728,34 +725,34 @@ private void initiateAttack(boolean replace, Object [] data) { private final void alterStateInternal(AIState newState, boolean replace, Object ...data) { switch (newState) { case ATTACK: initiateAttack(replace, data); - break; + break; case BANK: initiateBank(replace, data); - break; + break; case EVADE: initiateEvade(replace, data); break; case FLEE: initiateFlee(replace, data); - break; + break; case FLY_STRAIGHT: initiateStraight(replace, data); - break; + break; case FLY_PATH: initiatePath(replace, data); - break; + break; case IDLE: initiateIdle(replace, data); - break; + break; case TRACK: initiateTrack(replace, data); - break; - case MISSILE_TRACK: initiateMissileTrack(replace, data); + break; + case MISSILE_TRACK: initiateMissileTrack(replace, data); break; case FOLLOW_CURVE: initiateFollowCurve(replace, data); break; - default: break; - } + default: break; + } } - + final void setState(AIState newState, Object ...data) { alterStateInternal(newState, true, data); } - - final void pushState(AIState newState, Object ...data) { + + final void pushState(AIState newState, Object ...data) { alterStateInternal(newState, false, data); } @@ -767,11 +764,11 @@ final void popState() { AIState state = getState(); if (state == AIState.FOLLOW_CURVE) { // Make sure that an interrupted "follow curve" is not resumed. - popState(); + popState(); } } - - final void update(float deltaTime) { + + final void update(float deltaTime) { if (so != null) { if (so.escapeCapsuleCaps > 0 && so.getHullStrength() < 2 && !so.hasEjected()) { if (Math.random() * 100 < 10) { @@ -785,25 +782,53 @@ final void update(float deltaTime) { } so.updateSpeed(deltaTime); switch (currentState.peek()) { - case ATTACK: attackObject(deltaTime); - break; - case BANK: AliteLog.e("Updating bank state", "This should not happen..."); - break; - case EVADE: updateEvade(deltaTime); - break; - case FLEE: fleeObject(deltaTime); - break; - case FLY_STRAIGHT: flyStraight(deltaTime); - break; - case FLY_PATH: flyPath(deltaTime); - break; - case IDLE: return; - case TRACK: updateTrack(deltaTime); - break; - case FOLLOW_CURVE: followCurve(deltaTime); - break; - default: break; + case ATTACK: + attackObject(deltaTime); + break; + case BANK: + AliteLog.e("Updating bank state", "This should not happen..."); + break; + case EVADE: + updateEvade(deltaTime); + break; + case FLEE: + fleeObject(deltaTime); + break; + case FLY_STRAIGHT: + flyStraight(deltaTime); + break; + case FLY_PATH: + flyPath(deltaTime); + break; + case IDLE: + break; + case TRACK: + updateTrack(deltaTime); + break; + case FOLLOW_CURVE: + followCurve(deltaTime); + break; } + if (so instanceof CobraMkIII && ((CobraMkIII) so).isPlayerCobra()) { + String sl = ""; + switch (currentState.peek()) { + case ATTACK: sl = "AT"; break; + case BANK: sl = "BN"; break; + case EVADE: sl = "EV"; break; + case FLEE: sl = "FL"; break; + case FLY_STRAIGHT: sl = "FS"; break; + case FLY_PATH: sl = "FP"; break; + case IDLE: sl = "ID"; break; + case TRACK: sl = "TR"; break; + case FOLLOW_CURVE: sl = "FC"; break; + default: sl = "DE"; break; + } + AliteLog.e("AIS", "SOPATH: Player " + sl + " (" + so.getPosition().x + ":" + so.getPosition().y + ":" + so.getPosition().z + + ":" + so.getForwardVector().x + ":" + so.getForwardVector().y + ":" + so.getForwardVector().z + + ":" + so.getUpVector().x + ":" + so.getUpVector().y + ":" + so.getUpVector().z + + ":" + so.getRightVector().x + ":" + so.getRightVector().y + ":" + so.getRightVector().z + + ")"); + } } public AIState getState() { @@ -812,15 +837,15 @@ public AIState getState() { } return currentState.peek(); } - + public String getStateStack() { String stack = ""; for (int i = 0; i < currentState.size(); i++) { - stack += currentState.get(i) + ", "; + stack += currentState.get(i) + ", "; } return stack; } - + private void bankOrAttack(SpaceObject player) { AIState state = getState(); AliteLog.d("Object has been hit", "Object has been hit. Current State == " + state.name()); @@ -859,7 +884,7 @@ private void bankOrAttack(SpaceObject player) { pushState(AIState.BANK, player, true); } } - + private void flee(SpaceObject player) { if (getState() != AIState.FLEE) { if (Math.random() * 100 < FIRE_MISSILE_UPON_FIRST_HIT_PROBABILITY) { @@ -873,7 +898,7 @@ private void flee(SpaceObject player) { setState(AIState.FLEE, player); } } - + private void fleeBankOrAttack(SpaceObject player) { AIState state = getState(); if (state == AIState.ATTACK) { @@ -888,11 +913,11 @@ private void fleeBankOrAttack(SpaceObject player) { bankOrAttack(player); } else { flee(player); - } + } } // Else do nothing... } - + void executeHit(SpaceObject player) { if (so.getHullStrength() > 0 && !so.mustBeRemoved() && !so.hasEjected()) { int rand = (int) (Math.random() * 256); @@ -902,9 +927,9 @@ void executeHit(SpaceObject player) { so.setMissileCount(so.getMissileCount() - 1); so.addObjectToSpawn(ShipType.Missile); } - } + } } - + switch (so.getType()) { case Asteroid: break; // Nothing to do case CargoCanister: break; // Nothing to do @@ -920,5 +945,5 @@ void executeHit(SpaceObject player) { case Buoy: break; // Nothing to do case Platlet: break; // Nothing to do } - } + } } diff --git a/src/de/phbouillon/android/games/alite/screens/opengl/sprites/buttons/AliteButtons.java b/src/de/phbouillon/android/games/alite/screens/opengl/sprites/buttons/AliteButtons.java index 04e3f53..1bb4316 100644 --- a/src/de/phbouillon/android/games/alite/screens/opengl/sprites/buttons/AliteButtons.java +++ b/src/de/phbouillon/android/games/alite/screens/opengl/sprites/buttons/AliteButtons.java @@ -310,9 +310,9 @@ private void updateTorusDriveButton() { buttons[TORUS_DRIVE].active = true; if (alite.getCobra().getSpeed() < -PlayerCobra.TORUS_TEST_SPEED) { buttons[TORUS_DRIVE].yellow = true; - } else if (alite.getTimeFactor() > 1.0f) { + } else if (alite.getTimeFactor() > 1) { // time drive currently engaged, auto change to torus drive - alite.setTimeFactor(1.0f); + alite.setTimeFactor(1); engageTorusDrive(); buttons[TORUS_DRIVE].yellow = true; } else { @@ -336,14 +336,14 @@ private void updateTimeDriveButton() { inGame.getHud() != null && !inGame.isInSafeZone()) { // Check for Hud to compensate for brief flickering if come back from Information screen buttons[TIME_DRIVE].active = true; - buttons[TIME_DRIVE].yellow = alite.getTimeFactor() > 1.0f; + buttons[TIME_DRIVE].yellow = alite.getTimeFactor() > 1; } else { if (inGame.isDockingComputerActive()) { return; } buttons[TIME_DRIVE].active = false; - if (alite.getTimeFactor() > 1.0f) { - alite.setTimeFactor(1.0f); + if (alite.getTimeFactor() > 1) { + alite.setTimeFactor(1); } } } @@ -761,8 +761,8 @@ private void engageTimeDrive() { if (OVERRIDE_TORUS || alite.getCurrentScreen() instanceof TutorialScreen) { return; } - if ((alite.getTimeFactor() > 1.0f) || (ship.getSpeed() < -PlayerCobra.TORUS_TEST_SPEED)) { - alite.setTimeFactor(1.0f); + if ((alite.getTimeFactor() > 1) || (ship.getSpeed() < -PlayerCobra.TORUS_TEST_SPEED)) { + alite.setTimeFactor(1); } else { alite.setTimeFactor(PlayerCobra.SPEED_UP_FACTOR); }