From dd76b3acc3ebef7ff3bad91f7b44f0fb3dc22bc6 Mon Sep 17 00:00:00 2001 From: Enrico Fasoli Date: Tue, 1 Mar 2016 15:50:48 +0100 Subject: [PATCH] moved from single precision floating point to double precision --- core/src/com/mygdx/game/Game.java | 2 +- core/src/com/mygdx/game/Serializer.java | 34 +++++------ core/src/logic/Element.java | 28 ++++----- core/src/logic/Vegetable.java | 12 ++-- core/src/logic/World.java | 46 +++++++-------- core/src/logic/creatures/Beak.java | 20 +++---- core/src/logic/creatures/BodyPart.java | 22 +++---- core/src/logic/creatures/Creature.java | 34 +++++------ core/src/logic/creatures/Eye.java | 36 ++++++------ core/src/logic/creatures/Movement.java | 16 ++--- core/src/logic/creatures/Sight.java | 8 +-- core/src/logic/creatures/Torso.java | 32 +++++----- core/src/logic/neural/Brain.java | 42 ++++++------- core/src/logic/neural/Neuron.java | 38 ++++++------ core/src/logic/neural/NeuronCache.java | 14 ++--- desktop/src/gui/GUI.java | 78 ++++++++++++------------- 16 files changed, 231 insertions(+), 231 deletions(-) diff --git a/core/src/com/mygdx/game/Game.java b/core/src/com/mygdx/game/Game.java index 003725c..8064105 100644 --- a/core/src/com/mygdx/game/Game.java +++ b/core/src/com/mygdx/game/Game.java @@ -148,7 +148,7 @@ public class Game extends ApplicationAdapter { Creature c = world.getSelectedCreature(); renderer.setColor(1, 1, 1, 1); // Draw selection rectangle - renderer.rect(c.getX() - c.getSize(), c.getY() - c.getSize(), c.getSize() * 2, c.getSize() * 2); + renderer.rect((float) (c.getX() - c.getSize()), (float) (c.getY() - c.getSize()), (float) (c.getSize() * 2), (float) (c.getSize() * 2)); // Draw brain overlayRenderer.begin(); c.getBrain().render(overlayRenderer); diff --git a/core/src/com/mygdx/game/Serializer.java b/core/src/com/mygdx/game/Serializer.java index bc4a386..85cfcee 100644 --- a/core/src/com/mygdx/game/Serializer.java +++ b/core/src/com/mygdx/game/Serializer.java @@ -17,9 +17,9 @@ import java.util.Random; public class Serializer { private static final String[] sillabe = {"ba", "de", "ka", "mo", "shi", "du", "ro", "te", "mi", "lo", "pa"}; - private static Map defaults; + private static Map defaults; - public static String nameBrain(float[][][] brainMap) { + public static String nameBrain(double[][][] brainMap) { // Compute a unique representation of the brainmap long a = 0; for (int i = 0; i < brainMap.length; i++) { @@ -64,19 +64,19 @@ public class Serializer { return a; } - public static String serializeSettings(Map options) { + public static String serializeSettings(Map options) { String a = "# Settings file for use with AIrium.\n" + "# More information at http://github.com/fazo96/AIrium\n"; for (Object o : options.entrySet().toArray()) { - Map.Entry e = (Map.Entry) o; + Map.Entry e = (Map.Entry) o; a += e.getKey() + " = " + e.getValue() + "\n"; } return a; } - public static Map readSettings(String fileContent) { + public static Map readSettings(String fileContent) { int line = 0; - Map m = new HashMap(); + Map m = new HashMap(); for (String s : fileContent.split("\n")) { line++; if (s.startsWith("#")) { @@ -88,8 +88,8 @@ public class Serializer { if (ss.length != 2) { throw new Exception("Invalid string at line " + line); } - Log.log(Log.DEBUG, "Loading setting \"" + ss[0].trim() + "\" with value \"" + Float.parseFloat(ss[1].trim()) + "\""); - m.put(ss[0].trim(), Float.parseFloat(ss[1].trim())); + Log.log(Log.DEBUG, "Loading setting \"" + ss[0].trim() + "\" with value \"" + Double.parseDouble(ss[1].trim()) + "\""); + m.put(ss[0].trim(), Double.parseDouble(ss[1].trim())); } catch (Exception e) { Log.log(Log.ERROR, e.getMessage()); } @@ -97,7 +97,7 @@ public class Serializer { return m; } - public static String serializeBrain(float brainMap[][][]) { + public static String serializeBrain(double brainMap[][][]) { String s = "# Neural Map for use with AIrium.\n" + "# More information at http://github.com/fazo96/AIrium\n" + "Layers: " + (brainMap.length + 1); @@ -116,8 +116,8 @@ public class Serializer { return s; } - public static float[][][] loadBrain(String s) { - float brainMap[][][] = null; + public static double[][][] loadBrain(String s) { + double brainMap[][][] = null; Log.log(Log.INFO, "Loading brain from String with " + s.split("\n").length + " lines"); for (String l : s.split("\n")) { l = l.trim(); @@ -126,25 +126,25 @@ public class Serializer { } else if (l.startsWith("Layers: ")) { // Set Layer number int layers = Integer.parseInt(l.split(" ")[1]) - 1; - brainMap = new float[layers][][]; + brainMap = new double[layers][][]; Log.log(Log.INFO, "Loaded NLayers: " + layers); } else if (l.startsWith("Input Neurons")) { int in = Integer.parseInt(l.split(" ")[2]); - brainMap[0] = new float[in][0]; + brainMap[0] = new double[in][0]; Log.log(Log.INFO, "Loaded NInputNeurons: " + in); } else if (l.startsWith("Layer ")) { // Set neuron number for given layer String ll[] = l.split(" "); int layer = Integer.parseInt(ll[1]) - 2; int n = Integer.parseInt(ll[3]); - brainMap[layer] = new float[n][];//[layer>0?brainMap[layer-1].length:0]; + brainMap[layer] = new double[n][];//[layer>0?brainMap[layer-1].length:0]; } else if (l.startsWith("Weights ")) { // Set weights String ll[] = l.split(" "); int layer = Integer.parseInt(ll[3]) - 2; int neuron = Integer.parseInt(ll[5]) - 1; int nWeights = ll.length - 7; - brainMap[layer][neuron] = new float[nWeights]; + brainMap[layer][neuron] = new double[nWeights]; if (layer == 0) { Log.log(Log.DEBUG, "This weightmap is for brains with " + (nWeights) + " input neurons."); } else if (nWeights != brainMap[layer - 1].length) { @@ -154,7 +154,7 @@ public class Serializer { + " weights are supplied to this neuron"); } for (int i = 7; i < ll.length; i++) { - brainMap[layer][neuron][i - 7] = Float.parseFloat(ll[i]); + brainMap[layer][neuron][i - 7] = Double.parseDouble(ll[i]); Log.log(Log.DEBUG, "Loading L" + layer + "N" + neuron + "W" + (i - 7) + " = " + brainMap[layer][neuron][i - 7]); } Log.log(Log.DEBUG, "Loaded " + (nWeights) + " Weights for Layer " + layer + " Neuron " + neuron); @@ -164,7 +164,7 @@ public class Serializer { return brainMap; } - public static Map getDefaultSettings() { + public static Map getDefaultSettings() { if (defaults == null) { String s = "corpse_decay_rate = 0.0\n" + "mutationFactor = 1.0\n" diff --git a/core/src/logic/Element.java b/core/src/logic/Element.java index a4e7773..ece69e3 100644 --- a/core/src/logic/Element.java +++ b/core/src/logic/Element.java @@ -9,7 +9,7 @@ import com.badlogic.gdx.graphics.glutils.ShapeRenderer; */ public abstract class Element { - private float x, y, size; + private double x, y, size; /** * Create an element at given position with given radius. Elements have a @@ -19,7 +19,7 @@ public abstract class Element { * @param y the y position * @param size the element body radius */ - public Element(float x, float y, float size) { + public Element(double x, double y, double size) { this.x = x; this.y = y; this.size = size; @@ -35,8 +35,8 @@ public abstract class Element { * @return the distance from the element. It's 0 if they are just touching, * negative if they are colliding and positive if they are not */ - public float distanceFrom(Element e) { - return (float) Math.sqrt(Math.pow(e.x - x, 2) + Math.pow(e.y - y, 2)) - getSize() - e.getSize(); + public double distanceFrom(Element e) { + return Math.sqrt(Math.pow(e.x - x, 2) + Math.pow(e.y - y, 2)) - getSize() - e.getSize(); } /** @@ -58,8 +58,8 @@ public abstract class Element { * @param radius the radius of the circular object * @return true if the object overlaps this one */ - public boolean overlaps(float x, float y, float radius) { - return (float) Math.sqrt(Math.pow(x - this.x, 2) + Math.pow(y - this.y, 2)) < getSize() + radius; + public boolean overlaps(double x, double y, double radius) { + return Math.sqrt(Math.pow(x - this.x, 2) + Math.pow(y - this.y, 2)) < getSize() + radius; } /** @@ -69,7 +69,7 @@ public abstract class Element { * @param y the y position of the point to check * @return true if the point is part of this object's area */ - public boolean overlaps(float x, float y) { + public boolean overlaps(double x, double y) { return overlaps(x, y, 1); } @@ -79,7 +79,7 @@ public abstract class Element { * @param deltaX x translation * @param deltaY y translation */ - public void move(float deltaX, float deltaY) { + public void move(double deltaX, double deltaY) { x += deltaX; y += deltaY; } @@ -96,27 +96,27 @@ public abstract class Element { */ public abstract void render(ShapeRenderer s); - public float getX() { + public double getX() { return x; } - public float getY() { + public double getY() { return y; } - public float getSize() { + public double getSize() { return size; } - public void setX(float x) { + public void setX(double x) { this.x = x; } - public void setY(float y) { + public void setY(double y) { this.y = y; } - public void setSize(float size) { + public void setSize(double size) { this.size = size; } diff --git a/core/src/logic/Vegetable.java b/core/src/logic/Vegetable.java index 51a8416..b4b17f0 100644 --- a/core/src/logic/Vegetable.java +++ b/core/src/logic/Vegetable.java @@ -9,10 +9,10 @@ import com.mygdx.game.Game; */ public class Vegetable extends Element { - public static float default_radius = 5; - private float decayRate = 0; + public static double default_radius = 5; + private double decayRate = 0; - public Vegetable(float x, float y) { + public Vegetable(double x, double y) { super(x, y, default_radius); } @@ -27,14 +27,14 @@ public class Vegetable extends Element { @Override public void render(ShapeRenderer s) { s.setColor(1, 1, 1, 1); - s.circle(getX(), getY(), getSize()); + s.circle((float) getX(), (float) getY(), (float) getSize()); } - public float getDecayRate() { + public double getDecayRate() { return decayRate; } - public void setDecayRate(float decayRate) { + public void setDecayRate(double decayRate) { this.decayRate = decayRate; } } diff --git a/core/src/logic/World.java b/core/src/logic/World.java index e492d9f..247f410 100644 --- a/core/src/logic/World.java +++ b/core/src/logic/World.java @@ -30,11 +30,11 @@ import logic.neural.Brain; public class World implements Runnable { private int width, height, nPlants, creatPerGen; - private float nMutatedBrains = 0.2f, nMutatedNeurons = 0.5f, nMutatedConnections = 0.5f, mutationFactor = 1f; + private double nMutatedBrains = 0.2f, nMutatedNeurons = 0.5f, nMutatedConnections = 0.5f, mutationFactor = 1f; private int generation = 1; private boolean multithreading, cmdLaunchNewGen = false, cmdRestart = false; private int fpsLimit, fps = 0; - private Map options; + private Map options; private long ticksSinceGenStart = 0, maximumTicksPerGen = 0; private Creature selected; private Queue events = new LinkedList<>(); @@ -52,9 +52,9 @@ public class World implements Runnable { * @param options customization options. Can be null. See the * "reloadOptions" function for possible options */ - public World(Map options) { + public World(Map options) { if (options == null) { - this.options = new HashMap(); + this.options = new HashMap(); } else { this.options = options; } @@ -224,7 +224,7 @@ public class World implements Runnable { } Creature[] top = new Creature[topSize]; // Calculate avg fitness and prepare best agent list - float avgFitness = 0; + double avgFitness = 0; for (int i = 0; i < graveyard.size(); i++) { Creature c = graveyard.get(i); if (i < topSize) { @@ -243,7 +243,7 @@ public class World implements Runnable { while (sec == first && topSize > 1) { sec = (int) Math.floor(Math.random() * topSize); } - float[][][] n = null; + double[][][] n = null; try { n = top[first].getBrain().breed(top[sec].getBrain().getMap()); } catch (Exception ex) { @@ -274,15 +274,15 @@ public class World implements Runnable { */ public void reloadOptions() { for (Object o : Serializer.getDefaultSettings().entrySet().toArray()) { - Map.Entry e = (Map.Entry) o; + Map.Entry e = (Map.Entry) o; options.putIfAbsent(e.getKey(), e.getValue()); } - width = Math.round(options.get("world_width")); - height = Math.round(options.get("world_height")); - fpsLimit = Math.round(options.get("fps_limit")); + width = (int) Math.round(options.get("world_width")); + height = (int) Math.round(options.get("world_height")); + fpsLimit = (int) Math.round(options.get("fps_limit")); maximumTicksPerGen = Math.round(options.get("max_ticks")); - creatPerGen = Math.round(options.get("number_of_creatures")); - nPlants = Math.round(options.get("number_of_plants")); + creatPerGen = (int) Math.round(options.get("number_of_creatures")); + nPlants = (int) Math.round(options.get("number_of_plants")); multithreading = options.get("enable_multithreading") > 0; Creature.corpseDecayRate = options.get("corpse_decay_rate"); Creature.leaveCorpses = options.get("enable_corpses") > 0; @@ -297,8 +297,8 @@ public class World implements Runnable { Creature.hpForEatingPlants = options.get("creature_hp_for_eating_plants"); Creature.pointsForAttacking = options.get("creature_points_for_attacking"); Creature.pointsForEatingPlants = options.get("creature_points_for_eating_plants"); - Creature.brain_hidden_layers = Math.round(options.get("brain_hidden_layers")); - Creature.brain_hidden_neurons = Math.round(options.get("brain_hidden_neurons")); + Creature.brain_hidden_layers = (int) Math.round(options.get("brain_hidden_layers")); + Creature.brain_hidden_neurons = (int) Math.round(options.get("brain_hidden_neurons")); Brain.bias = options.get("brain_bias"); nMutatedBrains = options.get("nMutatedBrains"); nMutatedNeurons = options.get("nMutatedNeurons"); @@ -314,9 +314,9 @@ public class World implements Runnable { * null, a random mind will be created * @return the spawned element */ - private Element spawn(boolean isCreature, float[][][] brainMap) { + private Element spawn(boolean isCreature, double[][][] brainMap) { int x, y; - float r; + double r; boolean overlaps; if (isCreature) { r = Torso.default_radius; @@ -394,10 +394,10 @@ public class World implements Runnable { events.add(eventCode); } - public Queue getEventQueue(){ + public Queue getEventQueue() { return events; } - + public void spawnVegetable() { spawn(false, null); } @@ -406,7 +406,7 @@ public class World implements Runnable { return (Creature) spawn(true, null); } - public Creature spawnCreature(float[][][] b) { + public Creature spawnCreature(double[][][] b) { return (Creature) spawn(true, b); } @@ -446,7 +446,7 @@ public class World implements Runnable { return plants; } - public float getFpsLimit() { + public double getFpsLimit() { return fpsLimit; } @@ -454,11 +454,11 @@ public class World implements Runnable { this.fpsLimit = fpsLimit; } - public float getFps() { + public double getFps() { return fps; } - public Map getOptions() { + public Map getOptions() { return options; } @@ -478,7 +478,7 @@ public class World implements Runnable { this.multithreading = multithreading; } - public void replaceOptions(Map options) { + public void replaceOptions(Map options) { this.options = options; reloadOptions(); } diff --git a/core/src/logic/creatures/Beak.java b/core/src/logic/creatures/Beak.java index 576090a..883201a 100644 --- a/core/src/logic/creatures/Beak.java +++ b/core/src/logic/creatures/Beak.java @@ -14,18 +14,18 @@ import logic.Element; */ public class Beak extends BodyPart { - private float length; + private double length; private boolean attacking = false; - public static float max_length = Torso.default_radius / 4, min_length = max_length / 4; + public static double max_length = Torso.default_radius / 4, min_length = max_length / 4; - public Beak(float angle, Creature creature) { + public Beak(double angle, Creature creature) { super(3, 1, angle, 1, creature); length = min_length; } @Override - public float[] act() { - float r[] = new float[]{ + public double[] act() { + double r[] = new double[]{ length / max_length, // current beak length length > max_length / 2 ? 1f : 0f, // wether the beak is doing damage attacking ? 1f : 0f @@ -35,7 +35,7 @@ public class Beak extends BodyPart { } @Override - public void interactWithElement(Element e, float distance, float relAngle) { + public void interactWithElement(Element e, double distance, double relAngle) { if (e instanceof Creature && distance < length && length > max_length / 2 && Math.abs(relAngle) < 0.3f) { // Can attack creature.praise(Creature.pointsForAttacking); @@ -46,10 +46,10 @@ public class Beak extends BodyPart { } @Override - protected void draw(ShapeRenderer s, float relX, float relY) { + protected void draw(ShapeRenderer s, double relX, double relY) { s.set(ShapeRenderer.ShapeType.Line); // Draw Beak - s.setColor(getLength() / Beak.max_length, 1 - getLength() / Beak.max_length, 0, 1); + s.setColor((float) (getLength() / Beak.max_length), (float) (1 - getLength() / Beak.max_length), 0, 1); s.line((float) (relX + creature.getX()), (float) (relY + creature.getY()), (float) (relX * (1.5f + getLength() / Beak.max_length) + creature.getX()), (float) (relY * (1.5f + getLength() / Beak.max_length) + creature.getY())); if (attacking) { s.circle((float) (relX * (1.5f + getLength() / Beak.max_length) + creature.getX()), (float) (relY * (1.5f + getLength() / Beak.max_length) + creature.getY()), 0.3f); @@ -57,7 +57,7 @@ public class Beak extends BodyPart { } @Override - public void readFromBrain(float[] outputs) { + public void readFromBrain(double[] outputs) { length = outputs[0] * max_length; if (length > max_length) { length = max_length; @@ -66,7 +66,7 @@ public class Beak extends BodyPart { } } - public float getLength() { + public double getLength() { return length; } diff --git a/core/src/logic/creatures/BodyPart.java b/core/src/logic/creatures/BodyPart.java index ce8e64f..fa8559c 100644 --- a/core/src/logic/creatures/BodyPart.java +++ b/core/src/logic/creatures/BodyPart.java @@ -12,8 +12,8 @@ import logic.Element; public abstract class BodyPart { protected int inputNeuronsUsed; - protected float angle, distFromCenter; - protected float outputs[]; + protected double angle, distFromCenter; + protected double outputs[]; protected Creature creature; /** @@ -26,12 +26,12 @@ public abstract class BodyPart { * this body part * @param creature the creature that owns this body part */ - public BodyPart(int inputNeuronsUsed, int outputNeuronsUsed, float angle, float distFromCenter, Creature creature) { + public BodyPart(int inputNeuronsUsed, int outputNeuronsUsed, double angle, double distFromCenter, Creature creature) { this.inputNeuronsUsed = inputNeuronsUsed; this.angle = angle; this.distFromCenter = distFromCenter; this.creature = creature; - outputs = new float[outputNeuronsUsed]; + outputs = new double[outputNeuronsUsed]; } /** @@ -40,7 +40,7 @@ public abstract class BodyPart { * * @return the data to send to the brain, must be inputNeuronsUsed long */ - public abstract float[] act(); + public abstract double[] act(); /** * Interact with another element. This will be called every time the body @@ -52,7 +52,7 @@ public abstract class BodyPart { * @param distance the distance * @param relAngle the relative angle */ - public abstract void interactWithElement(Element e, float distance, float relAngle); + public abstract void interactWithElement(Element e, double distance, double relAngle); /** * Receive some data from the brain. This is called once every frame, after @@ -61,7 +61,7 @@ public abstract class BodyPart { * @param data the data received from the brain, will be outputNeuronsUsed * long */ - public abstract void readFromBrain(float data[]); + public abstract void readFromBrain(double data[]); /** * This will be called when the @@ -72,7 +72,7 @@ public abstract class BodyPart { * @param relY the Y position of this bodypart relative to the center its * creature */ - protected abstract void draw(ShapeRenderer s, float relX, float relY); + protected abstract void draw(ShapeRenderer s, double relX, double relY); /** * Prepares data and calls draw @@ -82,7 +82,7 @@ public abstract class BodyPart { public final void render(ShapeRenderer s) { double relX = Math.cos(creature.getDirection() + angle) * creature.getTorso().getRadius() * distFromCenter; double relY = Math.sin(creature.getDirection() + angle) * creature.getTorso().getRadius() * distFromCenter; - draw(s, (float) relX, (float) relY); + draw(s, (double) relX, (double) relY); } /** @@ -105,11 +105,11 @@ public abstract class BodyPart { * * @return the angle of this bodypart relative to the center of the creature */ - public float getAngle() { + public double getAngle() { return angle; } - public float getDistanceFromCreatureCenter() { + public double getDistanceFromCreatureCenter() { return distFromCenter; } diff --git a/core/src/logic/creatures/Creature.java b/core/src/logic/creatures/Creature.java index 9c2bf65..4c6dc62 100644 --- a/core/src/logic/creatures/Creature.java +++ b/core/src/logic/creatures/Creature.java @@ -20,13 +20,13 @@ import logic.neural.Brain; public abstract class Creature extends Element implements Runnable { public static int brain_hidden_layers = 2, brain_hidden_neurons = 10; - public static float corpseDecayRate = 0, pointsForEatingPlants = 1f, pointsForAttacking = 2f, hpForAttacking = 1f, hpForEatingPlants = 1f; + public static double corpseDecayRate = 0, pointsForEatingPlants = 1f, pointsForAttacking = 2f, hpForAttacking = 1f, hpForEatingPlants = 1f; public static boolean leaveCorpses = false; private final Brain brain; private final Torso torso; private final ArrayList bodyParts; - private float dir, fitness = 0; + private double dir, fitness = 0; private boolean workerDone = false, killWorker = false; private Thread workerThread; @@ -36,9 +36,9 @@ public abstract class Creature extends Element implements Runnable { * @param x * @param y */ - public Creature(float x, float y) { + public Creature(double x, double y) { super(x, y, Torso.default_radius); - dir = (float) (Math.random() * 2 * Math.PI); + dir = (double) (Math.random() * 2 * Math.PI); bodyParts = new ArrayList(); bodyParts.add(torso = new Torso(this)); buildBody(); @@ -77,10 +77,10 @@ public abstract class Creature extends Element implements Runnable { return; } // collect inputs - float values[] = new float[howManyInputNeurons()]; + double values[] = new double[howManyInputNeurons()]; int i = 0; for (BodyPart b : bodyParts) { - for (float v : b.act()) { + for (double v : b.act()) { values[i] = v; i++; } @@ -88,7 +88,7 @@ public abstract class Creature extends Element implements Runnable { // read from sensors and interact with world interactWithWorld(); // compute behavior - float[] actions = null; + double[] actions = null; try { actions = brain.compute(values); } catch (Exception ex) { @@ -99,7 +99,7 @@ public abstract class Creature extends Element implements Runnable { // Save brain outputs to body parts for (BodyPart b : bodyParts) { int n = 0; - float data[] = new float[b.getOutputNeuronsUsed()]; + double data[] = new double[b.getOutputNeuronsUsed()]; while (n < b.getOutputNeuronsUsed()) { data[n] = actions[i]; i++; @@ -122,8 +122,8 @@ public abstract class Creature extends Element implements Runnable { */ public void interactWithWorld() { for (Element e : Game.get().getWorld().getElements()) { - float distance = distanceFrom(e); - float angle = (float) (Math.atan2(getY() - e.getY(), getX() - e.getX())) - (dir - (float) Math.PI); + double distance = distanceFrom(e); + double angle = (double) (Math.atan2(getY() - e.getY(), getX() - e.getX())) - (dir - (double) Math.PI); for (BodyPart b : bodyParts) { b.interactWithElement(e, distance, angle); } @@ -146,7 +146,7 @@ public abstract class Creature extends Element implements Runnable { return n; } - public void rotate(float amount) { + public void rotate(double amount) { dir += amount; if (dir > 2 * Math.PI) { dir -= 2 * Math.PI; @@ -161,7 +161,7 @@ public abstract class Creature extends Element implements Runnable { * * @param amount how much */ - public void praise(float amount) { + public void praise(double amount) { fitness += amount; } @@ -189,9 +189,9 @@ public abstract class Creature extends Element implements Runnable { } } - public float getDangerLevel() { + public double getDangerLevel() { int beaks = 0; - float danger = 0; + double danger = 0; for (BodyPart b : bodyParts) { if (b instanceof Beak) { beaks++; @@ -217,15 +217,15 @@ public abstract class Creature extends Element implements Runnable { return brain; } - public void setDirection(float dir) { + public void setDirection(double dir) { this.dir = dir; } - public float getDirection() { + public double getDirection() { return dir; } - public float getFitness() { + public double getFitness() { return fitness; } diff --git a/core/src/logic/creatures/Eye.java b/core/src/logic/creatures/Eye.java index 3597b47..0b2ab6f 100644 --- a/core/src/logic/creatures/Eye.java +++ b/core/src/logic/creatures/Eye.java @@ -19,18 +19,18 @@ public class Eye extends BodyPart { private Sight sights[]; private int farthest = -1, seen; - private float farthestDistance = 0; - public static float fov = 2, sightRange = 30; + private double farthestDistance = 0; + public static double fov = 2, sightRange = 30; - public Eye(int nSights, float angle, Creature creature) { + public Eye(int nSights, double angle, Creature creature) { super(6 * nSights, 0, angle, 0.8f, creature); sights = new Sight[nSights]; seen = 0; } @Override - public float[] act() { - float ret[] = new float[inputNeuronsUsed]; + public double[] act() { + double ret[] = new double[inputNeuronsUsed]; int j = 0; for (int i = 0; i < sights.length; i++) { if (i < seen) { @@ -62,7 +62,7 @@ public class Eye extends BodyPart { } @Override - public void interactWithElement(Element e, float distance, float angle) { + public void interactWithElement(Element e, double distance, double angle) { if (e != creature && distance < sightRange && (distance < farthestDistance || seen < sights.length) && Math.abs(angle) < fov / 2) { if (seen < sights.length) { sights[seen] = new Sight(e, distance, angle); @@ -85,36 +85,36 @@ public class Eye extends BodyPart { } @Override - protected void draw(ShapeRenderer s, float relX, float relY) { + protected void draw(ShapeRenderer s, double relX, double relY) { // Draw eye s.setColor(1, 1, 1, 1); - s.circle(creature.getX() + relX, creature.getY() + relY, 3); + s.circle((float) (creature.getX() + relX), (float) (creature.getY() + relY), 3); // Draw FOV cone - float degrees = fov * 360f / (float) Math.PI; - float orient = (creature.getDirection() + angle) * 180f / (float) Math.PI - degrees / 2; - if (Game.get().getWorld().getOptions().getOrDefault("draw_view_cones", 0f) > 0) { + double degrees = fov * 360f / (double) Math.PI; + double orient = (creature.getDirection() + angle) * 180f / (double) Math.PI - degrees / 2; + if (Game.get().getWorld().getOptions().getOrDefault("draw_view_cones", 0d) > 0) { s.setColor(0.3f, 0.3f, 0.3f, 1); - s.arc((float) relX + creature.getX(), (float) relY + creature.getY(), sightRange, orient, degrees); + s.arc((float) (relX + creature.getX()), (float) (relY + creature.getY()), (float) sightRange, (float) orient, (float) degrees); } // Sight Lines - float c = 0; - if (Game.get().getWorld().getOptions().getOrDefault("draw_sight_lines", 0f) > 0) { + double c = 0; + if (Game.get().getWorld().getOptions().getOrDefault("draw_sight_lines", 0d) > 0) { for (Sight sight : sights) { if (sight != null) { c = sight.getDistance() / sightRange * 2 + sightRange; if (sight.getElement() instanceof Creature) { - s.setColor(c, 0, 0, 1); + s.setColor((float) c, 0, 0, 1); } else if (sight.getElement() instanceof Vegetable) { - s.setColor(0, c, 0, 1); + s.setColor(0, (float) c, 0, 1); } - s.line(relX + creature.getX(), creature.getY() + relY, sight.getElement().getX(), sight.getElement().getY()); + s.line((float) (relX + creature.getX()), (float) (creature.getY() + relY), (float) (sight.getElement().getX()), (float) (sight.getElement().getY())); } } } } @Override - public void readFromBrain(float[] data) { + public void readFromBrain(double[] data) { } } diff --git a/core/src/logic/creatures/Movement.java b/core/src/logic/creatures/Movement.java index c197469..735bb6e 100644 --- a/core/src/logic/creatures/Movement.java +++ b/core/src/logic/creatures/Movement.java @@ -16,15 +16,15 @@ import logic.Element; */ public class Movement extends BodyPart { - private float speed = 0, rotSpeed = 0; - public static float max_speed = 3; + private double speed = 0, rotSpeed = 0; + public static double max_speed = 3; public Movement(Creature creature) { super(0, 4, 0, 0, creature); } @Override - public float[] act() { + public double[] act() { if (speed > max_speed) { speed = max_speed; } @@ -32,7 +32,7 @@ public class Movement extends BodyPart { speed = -max_speed; } // apply speed - float xMul = (float) Math.cos(creature.getDirection()), yMul = (float) Math.sin(creature.getDirection()); + double xMul = (double) Math.cos(creature.getDirection()), yMul = (double) Math.sin(creature.getDirection()); creature.move(xMul * speed, yMul * speed); if (creature.getX() < 0) { creature.setX(Game.get().getWorld().getWidth() + creature.getX()); @@ -45,19 +45,19 @@ public class Movement extends BodyPart { creature.setY(creature.getY() - Game.get().getWorld().getHeight()); } creature.rotate(rotSpeed); - return new float[]{}; + return new double[]{}; } @Override - public void interactWithElement(Element e, float distance, float relAngle) { + public void interactWithElement(Element e, double distance, double relAngle) { } @Override - protected void draw(ShapeRenderer s, float relX, float relY) { + protected void draw(ShapeRenderer s, double relX, double relY) { } @Override - public void readFromBrain(float[] data) { + public void readFromBrain(double[] data) { Log.log(Log.DEBUG, "Fowward: " + data[0] + "Back: " + data[1] + " Rot: " + data[2] + " RotAnti: " + data[3]); speed = (data[0] * 2 - data[1] / 2) * max_speed; rotSpeed = data[2] - data[3]; diff --git a/core/src/logic/creatures/Sight.java b/core/src/logic/creatures/Sight.java index 27098a8..5ad366a 100644 --- a/core/src/logic/creatures/Sight.java +++ b/core/src/logic/creatures/Sight.java @@ -10,9 +10,9 @@ import logic.Element; public class Sight { private Element seen; - private float distance, angle; + private double distance, angle; - public Sight(Element seen, float distance, float angle) { + public Sight(Element seen, double distance, double angle) { this.seen = seen; this.distance = distance; this.angle = angle; @@ -22,11 +22,11 @@ public class Sight { return seen; } - public float getDistance() { + public double getDistance() { return distance; } - public float getAngle() { + public double getAngle() { return angle; } diff --git a/core/src/logic/creatures/Torso.java b/core/src/logic/creatures/Torso.java index 701f68a..7987ced 100644 --- a/core/src/logic/creatures/Torso.java +++ b/core/src/logic/creatures/Torso.java @@ -10,8 +10,8 @@ import logic.Vegetable; */ public class Torso extends BodyPart { - private float hp, prevHp, radius, pain = 0; - public static float default_radius = 20, max_hp = 100, hpDecay = 0.5f, eatingSpeed = 0.1f; + private double hp, prevHp, radius, pain = 0; + public static double default_radius = 20, max_hp = 100, hpDecay = 0.5f, eatingSpeed = 0.1f; private boolean eating = false; public Torso(Creature c) { @@ -22,9 +22,9 @@ public class Torso extends BodyPart { } @Override - public void draw(ShapeRenderer s, float x, float y) { - s.setColor(1 - (hp / max_hp), hp / max_hp, 0, 1); - s.circle(x + creature.getX(), y + creature.getY(), radius); + public void draw(ShapeRenderer s, double x, double y) { + s.setColor((float) (1 - (hp / max_hp)), (float) (hp / max_hp), 0, 1); + s.circle((float) (x + creature.getX()), (float) (y + creature.getY()), (float) radius); // Draw damage/heal marks s.set(ShapeRenderer.ShapeType.Filled); if (getReceivedDamage() > 0) { @@ -35,15 +35,15 @@ public class Torso extends BodyPart { s.setColor(0, 1, 0, 1); } if (getReceivedDamage() != 0 || eating) { - s.circle(x + creature.getX(), y + creature.getY(), 5); + s.circle((float) (x + creature.getX()), (float) (y + creature.getY()), 5); } } @Override - public float[] act() { + public double[] act() { // apply hunger hp -= hpDecay; - float r[] = new float[]{ + double r[] = new double[]{ hp/max_hp, eating ? 1f : 0f, pain @@ -55,7 +55,7 @@ public class Torso extends BodyPart { } @Override - public void interactWithElement(Element e, float distance, float relAngle) { + public void interactWithElement(Element e, double distance, double relAngle) { if (e instanceof Vegetable && distance < 0 && hp < max_hp) { e.setSize(e.getSize() - eatingSpeed); if (e.getSize() == 0) { @@ -68,7 +68,7 @@ public class Torso extends BodyPart { } @Override - public void readFromBrain(float[] data) { + public void readFromBrain(double[] data) { if (getReceivedDamage() > 0) { pain = -1; } else if (getReceivedDamage() < 0) { @@ -87,7 +87,7 @@ public class Torso extends BodyPart { * * @param amount how much to heal/damage */ - public void heal(float amount) { + public void heal(double amount) { hp += amount; if (hp < 0) { hp = 0; @@ -97,23 +97,23 @@ public class Torso extends BodyPart { } } - public float getReceivedDamage() { + public double getReceivedDamage() { return prevHp - hp; } - public float getRadius() { + public double getRadius() { return radius; } - public void setRadius(float radius) { + public void setRadius(double radius) { this.radius = radius; } - public float getHp() { + public double getHp() { return hp; } - public void setHp(float hp) { + public void setHp(double hp) { this.hp = hp; } diff --git a/core/src/logic/neural/Brain.java b/core/src/logic/neural/Brain.java index 30670f3..3c80224 100644 --- a/core/src/logic/neural/Brain.java +++ b/core/src/logic/neural/Brain.java @@ -11,7 +11,7 @@ import com.mygdx.game.Serializer; */ public class Brain { - public static float bias = 0.5f; + public static double bias = 0.5f; private Neuron[][] neurons; private String name; @@ -41,7 +41,7 @@ public class Brain { * * @param brainMap the new brain map to apply */ - public void remap(float[][][] brainMap) { + public void remap(double[][][] brainMap) { for (int i = 0; i < brainMap.length; i++) { // for each layer (skip input) for (int j = 0; j < brainMap[i].length; j++) { // for each neuron // skip input layer @@ -89,17 +89,17 @@ public class Brain { //s.set(ShapeRenderer.ShapeType.Line); for (int j = 0; j < neurons[i].length; j++) { // get neuron result first so cache system can kick in and save some calculations - float nr = neurons[i][j].compute(); + double nr = neurons[i][j].compute(); // Draw neuron links - float[] links = neurons[i][j].getWeights(); + double[] links = neurons[i][j].getWeights(); if (links != null) { for (int f = 0; f < links.length; f++) { - s.setColor(links[f] < 0 ? links[f] / 2 * -1 : 0, links[f] > 0 ? links[f] / 2 : 0, 0, 1); + s.setColor((float) (links[f] < 0 ? links[f] / 2 * -1 : 0), (float) (links[f] > 0 ? links[f] / 2 : 0), 0, 1); s.line(i * sepX + offset, j * sepY + offset, (i - 1) * sepX + offset, f * sepY + offset); } } // Draw neuron - s.setColor(1 - nr, nr, 0, 1); + s.setColor((float) (1 - nr), (float) nr, 0, 1); s.circle(i * sepX + offset, j * sepY + offset, 15); } } @@ -113,7 +113,7 @@ public class Brain { * @throws Exception if the number of inputs given differs from the number * of input neurons of this brain */ - public void input(float[] values) throws Exception { + public void input(double[] values) throws Exception { if (values.length != neurons[0].length) { throw new Exception("Brain has " + neurons[0].length + " input neurons," + " but was supplied with " @@ -130,9 +130,9 @@ public class Brain { * @return an array as long as the number of output neurons, containing the * result */ - public float[] compute() { + public double[] compute() { clearCache(); // unnecessary if already called when changing inputs - float[] res = new float[neurons[neurons.length - 1].length]; + double[] res = new double[neurons[neurons.length - 1].length]; for (int i = 0; i < neurons[neurons.length - 1].length; i++) { res[i] = neurons[neurons.length - 1][i].compute(); } @@ -147,7 +147,7 @@ public class Brain { * @throws Exception if the number of inputs given differs from the number * of input neurons of this brain */ - public float[] compute(float[] values) throws Exception { + public double[] compute(double[] values) throws Exception { input(values); return compute(); } @@ -158,11 +158,11 @@ public class Brain { * @return a tridimensional floating point number array representing a full * mind */ - public float[][][] getMap() { - float[][][] res = new float[neurons.length - 1][][]; + public double[][][] getMap() { + double[][][] res = new double[neurons.length - 1][][]; for (int i = 1; i < neurons.length; i++) // layers (skip input layer) { - res[i - 1] = new float[neurons[i].length][]; + res[i - 1] = new double[neurons[i].length][]; for (int j = 0; j < neurons[i].length; j++) // neurons per layer { res[i - 1][j] = neurons[i][j].getWeights(); @@ -181,11 +181,11 @@ public class Brain { * of mutated neurons (range: from 0 to 1) * @return a mutated brain map of this brain's mind */ - public float[][][] getMutatedMap(float mutationProbability, float connectionMutationProbability, float mutationFactor) { - float[][][] res = new float[neurons.length - 1][][]; + public double[][][] getMutatedMap(double mutationProbability, double connectionMutationProbability, double mutationFactor) { + double[][][] res = new double[neurons.length - 1][][]; for (int i = 1; i < neurons.length; i++) // layers (skip input layer) { - res[i - 1] = new float[neurons[i].length][]; + res[i - 1] = new double[neurons[i].length][]; for (int j = 0; j < neurons[i].length; j++) // neurons per layer { if (Math.random() <= mutationProbability) { @@ -205,7 +205,7 @@ public class Brain { * of mutated neurons (range: from 0 to 1) * @param mutationFactor the higher this number, the bigger the mutation */ - public void mutate(float mutationProbability, float connectionMutationProbability, float mutationFactor) { + public void mutate(double mutationProbability, double connectionMutationProbability, double mutationFactor) { for (int i = 1; i < neurons.length; i++) // layers (skip input layer) { for (int j = 0; j < neurons[i].length; j++) // neurons per layer @@ -228,20 +228,20 @@ public class Brain { * @throws Exception if the brains don't have identical neuron and layer * numbers */ - public float[][][] breed(float[][][] map) throws Exception { - float[][][] res = new float[neurons.length - 1][][]; + public double[][][] breed(double[][][] map) throws Exception { + double[][][] res = new double[neurons.length - 1][][]; if (map.length != neurons.length - 1) { throw new Exception("incompatible brains"); } for (int i = 1; i < neurons.length; i++) // layers (skip input layer) { - res[i - 1] = new float[neurons[i].length][]; + res[i - 1] = new double[neurons[i].length][]; if (map[i - 1].length != neurons[i].length) { throw new Exception("incompatible brains"); } for (int j = 0; j < neurons[i].length; j++) // neurons per layer { - res[i - 1][j] = new float[neurons[i][j].getWeights().length]; + res[i - 1][j] = new double[neurons[i][j].getWeights().length]; if (map[i - 1][j].length != neurons[i][j].getWeights().length) { throw new Exception("incompatible brains"); } diff --git a/core/src/logic/neural/Neuron.java b/core/src/logic/neural/Neuron.java index 6ec13b9..15da78a 100644 --- a/core/src/logic/neural/Neuron.java +++ b/core/src/logic/neural/Neuron.java @@ -11,9 +11,9 @@ import java.util.logging.Logger; */ public class Neuron { - private float[] weights; + private double[] weights; private NeuronCache cache; - private float bias, output; + private double bias, output; private boolean isInputNeuron; private int layer, receivesFromLayer; private Brain brain; @@ -28,7 +28,7 @@ public class Neuron { * neurons) * @param brain the brain which contains this neuron */ - public Neuron(int layer, int receivesFromLayer, float bias, Brain brain) { + public Neuron(int layer, int receivesFromLayer, double bias, Brain brain) { this(layer, receivesFromLayer, bias, brain, null); } @@ -43,7 +43,7 @@ public class Neuron { * @param brain the brain which contains this neuron * @param weights the weights to use to configure this neuron */ - public Neuron(int layer, int receivesFromLayer, float bias, Brain brain, float[] weights) { + public Neuron(int layer, int receivesFromLayer, double bias, Brain brain, double[] weights) { this.brain = brain; this.layer = layer; this.receivesFromLayer = receivesFromLayer; @@ -65,14 +65,14 @@ public class Neuron { private void scramble() { // init weights if (layer > 0) { - weights = new float[brain.getNeurons()[receivesFromLayer].length]; + weights = new double[brain.getNeurons()[receivesFromLayer].length]; } else { // layer 0 or negative isInputNeuron = true; - weights = new float[0]; + weights = new double[0]; } // Put random weights for (int i = 0; i < weights.length; i++) { - weights[i] = (float) (Math.random() * 5 - 2.5f); + weights[i] = (double) (Math.random() * 5 - 2.5f); } } @@ -84,7 +84,7 @@ public class Neuron { * * @return the output of this neuron. */ - public float compute() { + public double compute() { if (weights == null || weights.length == 0) { isInputNeuron = true; } @@ -94,7 +94,7 @@ public class Neuron { if (cache.hasCachedOutput()) { return cache.getCachedOutput(); } - float a = bias * -1; // activation + double a = bias * -1; // activation for (int i = 0; i < weights.length; i++) { if (cache.has(i)) { try { @@ -105,13 +105,13 @@ public class Neuron { } } else { Neuron n = brain.getNeurons()[receivesFromLayer][i]; - float v = n.compute() * weights[i]; + double v = n.compute() * weights[i]; a += v; cache.put(i, v); } } // sigmoid function - float res = (float) (1 / (1 + Math.pow(Math.E, a * -1))); + double res = (double) (1 / (1 + Math.pow(Math.E, a * -1))); cache.setCachedOutput(res); Log.log(Log.DEBUG, "Computed Value " + res + " for neuron"); return res; @@ -124,11 +124,11 @@ public class Neuron { * @param mutationFactor controls how much weights mutate * @return the new weights */ - public float[] getMutatedWeights(float mutationProbability, float mutationFactor) { - float[] mutatedWeights = new float[weights.length]; + public double[] getMutatedWeights(double mutationProbability, double mutationFactor) { + double[] mutatedWeights = new double[weights.length]; for (int i = 0; i < weights.length; i++) { if (Math.random() <= mutationProbability) { - mutatedWeights[i] = weights[i] + (float) (Math.random() * mutationFactor) - mutationFactor / 2; + mutatedWeights[i] = weights[i] + (double) (Math.random() * mutationFactor) - mutationFactor / 2; } else { mutatedWeights[i] = weights[i]; } @@ -141,16 +141,16 @@ public class Neuron { * * @param output the output you want to set */ - public void setOutput(float output) { + public void setOutput(double output) { isInputNeuron = true; this.output = output; } - public float getBias() { + public double getBias() { return bias; } - public void setBias(float bias) { + public void setBias(double bias) { this.bias = bias; } @@ -166,7 +166,7 @@ public class Neuron { this.layer = layer; } - public float[] getWeights() { + public double[] getWeights() { return weights; } @@ -175,7 +175,7 @@ public class Neuron { * * @param weights the new weights to put */ - public void setWeights(float[] weights) { + public void setWeights(double[] weights) { this.weights = weights; // Changing the neuron makes the cache invalid clearCache(); diff --git a/core/src/logic/neural/NeuronCache.java b/core/src/logic/neural/NeuronCache.java index 07b4bd9..34f55f1 100644 --- a/core/src/logic/neural/NeuronCache.java +++ b/core/src/logic/neural/NeuronCache.java @@ -7,8 +7,8 @@ package logic.neural; */ public class NeuronCache { - private float[] cache; - private float cachedOutput; + private double[] cache; + private double cachedOutput; private boolean cachedOutputValid; private boolean[] validity; @@ -18,7 +18,7 @@ public class NeuronCache { * @param size how many inputs the requiring neuron has. */ public NeuronCache(int size) { - cache = new float[size]; + cache = new double[size]; validity = new boolean[size]; clear(); } @@ -29,7 +29,7 @@ public class NeuronCache { * @param index the index of the value * @param value the value itself */ - public void put(int index, float value) { + public void put(int index, double value) { validity[index] = true; cache[index] = value; } @@ -41,7 +41,7 @@ public class NeuronCache { * @return the value required * @throws Exception if value not stored or declared invalid */ - public float get(int index) throws Exception { + public double get(int index) throws Exception { if (validity[index]) { return cache[index]; } else { @@ -59,7 +59,7 @@ public class NeuronCache { return validity[index]; } - public float getCachedOutput() { + public double getCachedOutput() { return cachedOutput; } @@ -67,7 +67,7 @@ public class NeuronCache { return cachedOutputValid; } - public void setCachedOutput(float cachedOutput) { + public void setCachedOutput(double cachedOutput) { this.cachedOutput = cachedOutput; } diff --git a/desktop/src/gui/GUI.java b/desktop/src/gui/GUI.java index 1f0cf27..ff80c20 100644 --- a/desktop/src/gui/GUI.java +++ b/desktop/src/gui/GUI.java @@ -49,7 +49,7 @@ public class GUI extends javax.swing.JFrame implements LogListener { private boolean shouldUpdateGUI = false; private final Thread guiUpdater; private final Listener listener; - private Map options; + private Map options; private boolean updatingSliders = false, updatingTable = false; /** @@ -67,7 +67,7 @@ public class GUI extends javax.swing.JFrame implements LogListener { updateGUI(); } }; - options = new HashMap(); + options = new HashMap(); world = new World(options); updateSettingsUI(); settingsTable.getModel().addTableModelListener(new TableModelListener() { @@ -965,25 +965,25 @@ public class GUI extends javax.swing.JFrame implements LogListener { */ private void saveSliderChanges() { if (!updatingSliders) { - options.put("fps_limit", toggleFPSLimitCheckbox.isSelected() ? 0 : (float) fpsLimitSlider.getValue()); - options.put("enable_multithreading", multithreadingCheckbox.isSelected() ? 1f : 0f); - options.put("number_of_creatures", (float) nCreaturesSlider.getValue()); - options.put("number_of_plants", (float) nPlantsSlider.getValue()); - options.put("corpse_decay_rate", corpseDecaySlider.getValue() / 1000f); - options.put("enable_corpses", enableCorpsesCheckbox.isSelected() ? 1f : 0f); - options.put("world_width", (float) worldSizeSlider.getValue()); - options.put("world_height", (float) worldSizeSlider.getValue()); + options.put("fps_limit", toggleFPSLimitCheckbox.isSelected() ? 0d : fpsLimitSlider.getValue()); + options.put("enable_multithreading", multithreadingCheckbox.isSelected() ? 1d : 0d); + options.put("number_of_creatures", (double) nCreaturesSlider.getValue()); + options.put("number_of_plants", (double) nPlantsSlider.getValue()); + options.put("corpse_decay_rate", (double) corpseDecaySlider.getValue() / 1000d); + options.put("enable_corpses", enableCorpsesCheckbox.isSelected() ? 1d : 0d); + options.put("world_width", (double) worldSizeSlider.getValue()); + options.put("world_height", (double) worldSizeSlider.getValue()); topSizeSlider.setMaximum(nCreaturesSlider.getValue()); - options.put("parents_count", (float) topSizeSlider.getValue()); - options.put("creature_sight_range", (float) sightRangeSlider.getValue()); - options.put("creature_hp_decay", (float) hpDecaySlider.getValue() / 1000); - options.put("max_ticks", (float) maxTicksSlider.getValue()); - options.put("draw_view_cones", drawViewCones.isSelected() ? 1f : 0); - options.put("draw_sight_lines", drawSightLines.isSelected() ? 1f : 0); - options.put("nMutatedBrains", (float) nMutatedBrainsSlider.getValue() / 100); - options.put("nMutatedNeurons", (float) nMutatedNeuronsSlider.getValue() / 100); - options.put("nMutatedConnections", (float) nMutatedConnectionsSlider.getValue() / 100); - options.put("mutationFactor", (float) mutationFactorSlider.getValue() / 100); + options.put("parents_count", (double) topSizeSlider.getValue()); + options.put("creature_sight_range", (double) sightRangeSlider.getValue()); + options.put("creature_hp_decay", hpDecaySlider.getValue() / 1000d); + options.put("max_ticks", (double) maxTicksSlider.getValue()); + options.put("draw_view_cones", drawViewCones.isSelected() ? 1d : 0d); + options.put("draw_sight_lines", drawSightLines.isSelected() ? 1d : 0d); + options.put("nMutatedBrains", nMutatedBrainsSlider.getValue() / 100d); + options.put("nMutatedNeurons", nMutatedNeuronsSlider.getValue() / 100d); + options.put("nMutatedConnections", nMutatedConnectionsSlider.getValue() / 100d); + options.put("mutationFactor", mutationFactorSlider.getValue() / 100d); world.reloadOptions(); } updateSettingsUI(); @@ -1167,7 +1167,7 @@ public class GUI extends javax.swing.JFrame implements LogListener { if (f == null) { return; } - float map[][][] = Serializer.loadBrain(Serializer.loadFromFile(f)); + double map[][][] = Serializer.loadBrain(Serializer.loadFromFile(f)); Creature c = (Creature) world.spawnCreature(map); world.selectCreature(c); updateGUI(); @@ -1213,7 +1213,7 @@ public class GUI extends javax.swing.JFrame implements LogListener { private void saveTableChanges() { for (int row = 0; row < settingsTable.getRowCount(); row++) { - options.put((String) settingsTable.getValueAt(row, 0), (Float) settingsTable.getValueAt(row, 1)); + options.put((String) settingsTable.getValueAt(row, 0), Double.parseDouble((String) settingsTable.getValueAt(row, 1))); } world.reloadOptions(); updateSettingsUI(); @@ -1224,7 +1224,7 @@ public class GUI extends javax.swing.JFrame implements LogListener { */ private void updateSettingsUI() { updatingSliders = true; - int fps = Math.round(options.get("fps_limit")); + int fps = (int) Math.round(options.get("fps_limit")); if (fps < 1) { fpsLimitSlider.setValue(60); toggleFPSLimitCheckbox.setSelected(true); @@ -1233,34 +1233,34 @@ public class GUI extends javax.swing.JFrame implements LogListener { toggleFPSLimitCheckbox.setSelected(false); } multithreadingCheckbox.setSelected(options.get("enable_multithreading") > 0f); - nCreaturesSlider.setValue(Math.round(options.get("number_of_creatures"))); + nCreaturesSlider.setValue((int) Math.round(options.get("number_of_creatures"))); topSizeSlider.setMaximum(nCreaturesSlider.getValue()); - topSizeSlider.setValue(Math.round(options.get("parents_count"))); - nPlantsSlider.setValue(Math.round(options.get("number_of_plants"))); - corpseDecaySlider.setValue(Math.round(options.get("corpse_decay_rate") * 1000)); + topSizeSlider.setValue((int) Math.round(options.get("parents_count"))); + nPlantsSlider.setValue((int) Math.round(options.get("number_of_plants"))); + corpseDecaySlider.setValue((int) Math.round(options.get("corpse_decay_rate") * 1000)); enableCorpsesCheckbox.setSelected(options.get("enable_corpses") > 0f); - worldSizeSlider.setValue(Math.round(options.get("world_height"))); - sightRangeSlider.setValue(Math.round(options.get("creature_sight_range"))); - hpDecaySlider.setValue(Math.round(options.get("creature_hp_decay") * 1000)); - maxTicksSlider.setValue(Math.round(options.get("max_ticks"))); + worldSizeSlider.setValue((int) Math.round(options.get("world_height"))); + sightRangeSlider.setValue((int) Math.round(options.get("creature_sight_range"))); + hpDecaySlider.setValue((int) Math.round(options.get("creature_hp_decay") * 1000)); + maxTicksSlider.setValue((int) Math.round(options.get("max_ticks"))); drawViewCones.setSelected(options.get("draw_view_cones") > 0f); drawSightLines.setSelected(options.get("draw_sight_lines") > 0f); - nMutatedBrainsSlider.setValue(Math.round(options.get("nMutatedBrains") * 100)); - nMutatedNeuronsSlider.setValue(Math.round(options.get("nMutatedNeurons") * 100)); - nMutatedConnectionsSlider.setValue(Math.round(options.get("nMutatedConnections") * 100)); - mutationFactorSlider.setValue(Math.round(options.get("mutationFactor") * 100)); + nMutatedBrainsSlider.setValue((int) Math.round(options.get("nMutatedBrains") * 100)); + nMutatedNeuronsSlider.setValue((int) Math.round(options.get("nMutatedNeurons") * 100)); + nMutatedConnectionsSlider.setValue((int) Math.round(options.get("nMutatedConnections") * 100)); + mutationFactorSlider.setValue((int) Math.round(options.get("mutationFactor") * 100)); updatingSliders = false; - currentNMutatedNeurons.setText(String.format("%.2f", (float) nMutatedNeuronsSlider.getValue() / 100) + "%"); + currentNMutatedNeurons.setText(String.format("%.2f", nMutatedNeuronsSlider.getValue() / 100d) + "%"); currentSightRange.setText(sightRangeSlider.getValue() + ""); - currentNMutatedBrains.setText(String.format("%.2f", (float) nMutatedBrainsSlider.getValue() / 100) + "%"); + currentNMutatedBrains.setText(String.format("%.2f", nMutatedBrainsSlider.getValue() / 100d) + "%"); currentWorldSize.setText(worldSizeSlider.getValue() + ""); currentTopSize.setText(topSizeSlider.getValue() + (topSizeSlider.getValue() <= 0 ? " (Auto)" : "")); currentMaxTicks.setText(maxTicksSlider.getValue() + ""); currentHpDecay.setText(hpDecaySlider.getValue() / 1000f + ""); - currentMutationFactor.setText(String.format("%.2f", (float) mutationFactorSlider.getValue() / 100)); + currentMutationFactor.setText(String.format("%.2f", mutationFactorSlider.getValue() / 100d)); currentFpsLimit.setText("" + fpsLimitSlider.getValue()); currentNCreatures.setText(nCreaturesSlider.getValue() + ""); - currentNMutatedConnections.setText(String.format("%.2f", (float) nMutatedConnectionsSlider.getValue() / 100) + "%"); + currentNMutatedConnections.setText(String.format("%.2f", nMutatedConnectionsSlider.getValue() / 100d) + "%"); currentNPlants.setText(nPlantsSlider.getValue() + ""); currentCorpseDecay.setText(corpseDecaySlider.getValue() / 1000f + ""); int row = 0;