public APCircleWindow() {
    super("AP Circles");
    setDefaultCloseOperation(EXIT_ON_CLOSE);

    String startDirectoryName = System.getProperty("user.dir");
    startDirectory = new File(startDirectoryName);
    // this for convenience, as the program normally starts in graph/display
    //		startDirectory = startDirectory.getParentFile();

    gw = this;

    generalXML = new GeneralXML(graph);

    gp = new APCirclePanel(this);
    getContentPane().add(gp);

    graph = gp.getGraph();

    initView();
    initExperiment();
    initUtility();
    initLayout();
    initMenu();

    setSize(width, height);

    Dimension frameDim = Toolkit.getDefaultToolkit().getScreenSize();
    int posX = (frameDim.width - getSize().width) / 2;
    int posY = (frameDim.height - getSize().height) / 2;
    setLocation(posX, posY);

    setVisible(true);

    gp.requestFocus();
  }
Exemple #2
0
  public void restartApplication() {

    try {

      final String javaBin =
          System.getProperty("java.home") + File.separator + "bin" + File.separator + "javaw";
      final File currentJar =
          new File(network.class.getProtectionDomain().getCodeSource().getLocation().toURI());

      System.out.println("javaBin " + javaBin);
      System.out.println("currentJar " + currentJar);
      System.out.println("currentJar.getPath() " + currentJar.getPath());

      /* is it a jar file? */
      // if(!currentJar.getName().endsWith(".jar")){return;}

      try {

        // xmining = 0;
        // systemx.shutdown();

      } catch (Exception e) {
        e.printStackTrace();
      }

      /* Build command: java -jar application.jar */
      final ArrayList<String> command = new ArrayList<String>();
      command.add(javaBin);
      command.add("-jar");
      command.add("-Xms256m");
      command.add("-Xmx1024m");
      command.add(currentJar.getPath());

      final ProcessBuilder builder = new ProcessBuilder(command);
      builder.start();

      // try{Thread.sleep(10000);} catch (InterruptedException e){}

      // close and exit
      SystemTray.getSystemTray().remove(network.icon);
      System.exit(0);

    } // try
    catch (Exception e) {
      JOptionPane.showMessageDialog(null, e.getCause());
    }
  } // ******************************
public class GameCharacter {
  // Position and Size
  public double X = 0, Y = 0;
  public double W = 0, H = 0;
  // Frames
  public int FX = 0, FY = 0;

  // Where to find character sprites
  String DIRECT = System.getProperty("user.dir") + "\\Graphics\\Character\\";
  String DIRECT2 = System.getProperty("user.dir") + "\\Graphics\\Effects\\";

  // Max number of frames
  int SIZE = 0;

  // Used for delay in framechange()
  int COUNTER = 0;

  // Sprite Type
  int TYPE = 1;

  // Sprite
  BufferedImage imgCHARAC, imgBLOOD, imgQStart, imgQEnd;

  // Collision maps
  Vector<GridMap> MAP = new Vector<GridMap>();

  // Collision objects
  Vector<GameObject> OBJECTS = new Vector<GameObject>();

  // Collision characters
  Vector<GameCharacter> CHARACTERS = new Vector<GameCharacter>();

  // Collision characters
  Vector<Building> BUILD = new Vector<Building>();

  // Spells
  Vector<MagicAttack[]> SPELL_LIST = new Vector<MagicAttack[]>();

  Vector<Quest> QUEST_LIST = new Vector<Quest>();

  // Size
  double GROWTHFACTOR = 1;

  // Create character inventory
  ItemList INVENTORY = new ItemList();

  // Character class
  String CLASS = "", Cl = "";

  // Basic stats
  double MAX_HEALTH = 100, MAX_MANA = 100;
  int HEALTH = (int) MAX_HEALTH, MANA = (int) MAX_MANA, GOLD = 0;

  // Movement
  int REGEN_COUNTER = 0, SPEED = 1;

  // Used for magic attacks
  int MAGIC_COUNTER = 0;

  // Possible AIs
  NPCAI NAI;
  EnemyAI EAI;

  // Restrictions
  boolean ISDEAD = false, COLL_LISTENER = false, CANMOVE = true;

  // List of available magic attacks
  MagicAttack[] FIREBALL = new MagicAttack[11],
      SHOCK = new MagicAttack[11],
      DARKNESS = new MagicAttack[11],
      LIFE_DRAIN = new MagicAttack[11];

  // Character Stats
  Stats STATS = new Stats(this);

  // Weapons and armor
  MeeleAttack MEELE_WEAPON = new MeeleAttack(0, 0, "Sword_1.png", this);
  Image SHIELD = null;

  // Death sound
  AudioEffects audDEATH = new AudioEffects(false);

  // Progress bar used for basic tasks
  ProgressBar BASIC_PROCESS, BASIC_EFFECTS;
  int SPAWN_X = -1, SPAWN_Y = -1;

  /**
   * Constructor to create a character
   *
   * @param x X Position
   * @param y Y Position
   * @param w Width of Image
   * @param h Height of Image
   * @param FileN Name of image file
   * @param S Max number of frames
   */
  public GameCharacter(
      double x, double y, double w, double h, String FileN, int S, int Ty, String c) {
    // Set position and size
    X = x;
    Y = y;
    W = w;
    H = h;

    BASIC_PROCESS = new ProgressBar(new Font("Arial", 36, 36), this);
    BASIC_EFFECTS = new ProgressBar(new Font("Arial", 36, 36), this);
    // Add magic attacks
    // Fireball
    for (int i = 0; i < FIREBALL.length; i++) {
      FIREBALL[i] = new MagicAttack(-500, -500, 39, 41, "Fireball.png", 3, 1, 2, "Fireball");
      FIREBALL[i].STATS.setStats(new String[] {"Damage=10", "Points=10"});
      FIREBALL[i].CASTER = this;
    }
    // Shock
    for (int i = 0; i < SHOCK.length; i++) {
      SHOCK[i] = new MagicAttack(-500, -500, 39, 41, "Shock.png", 2, 1, 0, "Shock");
      SHOCK[i].STATS.setStats(new String[] {"Damage=20", "Points=15"});
      SHOCK[i].CASTER = this;
    }
    // Darkness
    for (int i = 0; i < DARKNESS.length; i++) {
      DARKNESS[i] = new MagicAttack(-500, -500, 165, 164, "Darkness.png", 3, 1, 2, "Darkness");
      DARKNESS[i].STATS.setStats(new String[] {"Damage=100", "Points=50"});
      DARKNESS[i].CASTER = this;
    }
    // Life Drain
    for (int i = 0; i < LIFE_DRAIN.length; i++) {
      LIFE_DRAIN[i] = new MagicAttack(-500, -500, 32, 32, "Life Drain.png", 7, 1, 0, "Life Drain");
      LIFE_DRAIN[i].STATS.setStats(new String[] {"Damage=50", "Points=25"});
      LIFE_DRAIN[i].CASTER = this;
    }
    // Get Image
    try {

      if (isJar()) {
        // Character
        imgCHARAC = getImage("/Graphics/Character/", FileN);

        // Blood
        int BloodType = (int) Math.round(Math.random() * 3) + 1;
        imgBLOOD = getImage("/Graphics/Effects/", "Dead" + BloodType + ".png");

        // Quest
        imgQStart = getImage("/Graphics/Effects/", "Quest_Start.png");
        imgQEnd = getImage("/Graphics/Effects/", "Quest_Complete.png");

      } else {
        // Character
        imgCHARAC = ImageIO.read(Paths.get(DIRECT + FileN).toFile());

        // Blood
        int BloodType = (int) Math.round(Math.random() * 3) + 1;
        imgBLOOD = ImageIO.read(Paths.get(DIRECT2 + "Dead" + BloodType + ".png").toFile());

        // Quest
        imgQStart = ImageIO.read(Paths.get(DIRECT2 + "Quest_Start.png").toFile());
        imgQEnd = ImageIO.read(Paths.get(DIRECT2 + "Quest_Complete.png").toFile());
      }

    } catch (Exception e) {
    }

    // Max number of frames
    SIZE = S;

    // Sprite type
    TYPE = Ty;

    // Assign class
    CLASS = c;
    Cl = c;

    // Add items and attacks according to class
    if (CLASS.equals("Player")) {

      // Add items
      INVENTORY.addItem(
          "Health Potion", 25, 1, "Health Pot.png", "Potion", new String[] {"Points=50"});
      INVENTORY.addItem(
          "Rusted Dagger",
          20,
          1,
          "Dagger_4.png",
          "Meele",
          new String[] {"Damage=10", "Attack Speed=1"});
      INVENTORY.addItem(
          "Wooden Staff",
          20,
          1,
          "Staff_1.png",
          "Meele",
          new String[] {"Damage=5", "Attack Speed=1"});

      // Equip items
      INVENTORY.ItemEffect(1, this);
      // MEELE_WEAPON=null;
      // Assign Magic
      SPELL_LIST.add(FIREBALL);

      // Inventory type
      INVENTORY.Type = "Player";
    } else if (CLASS.equals("Citizen")) {

      // Add items
      INVENTORY.addItem(
          "Health Potion", 25, 1, "Health Pot.png", "Potion", new String[] {"Points=50"});

      // Add Ai
      NAI = new NPCAI(this);

      // Add Gold
      this.GOLD = (int) Math.round(Math.random() * 15 + 5);

      INVENTORY.Type = "Friendly";
    } else if (CLASS.equals("Blacksmith")) {

      // Add items
      INVENTORY.addItem(
          "Silver Dagger",
          250,
          1,
          "Dagger_3.png",
          "Meele",
          new String[] {"Damage=10", "Attack Speed=1"});
      INVENTORY.addItem(
          "Steel Dagger",
          450,
          1,
          "Dagger_5.png",
          "Meele",
          new String[] {"Damage=35", "Attack Speed=1"});
      // INVENTORY.addItem("Assassin blade", 750,1, "Dagger_6.png","Meele",new
      // String[]{"Damage=45","Attack Speed=1"});
      // INVENTORY.addItem("Serpent Dagger", 5000,1, "Dagger_2.png","Meele",new
      // String[]{"Damage=50","Attack Speed=1"});
      // INVENTORY.addItem("Dagger of Time", 5050,1, "Dagger_1.png","Meele",new
      // String[]{"Damage=75","Attack Speed=1"});

      INVENTORY.addItem(
          "Steel Sword",
          450,
          1,
          "Sword_1.png",
          "Meele",
          new String[] {"Damage=30", "Attack Speed=0.65"});
      INVENTORY.addItem(
          "Iron Sword",
          50,
          1,
          "Sword_2.png",
          "Meele",
          new String[] {"Damage=15", "Attack Speed=0.65"});
      INVENTORY.addItem(
          "Silver Sword",
          100,
          1,
          "Sword_5.png",
          "Meele",
          new String[] {"Damage=20", "Attack Speed=0.5"});
      // INVENTORY.addItem("Iron Scimitar", 150,1, "Sword_7.png","Meele",new
      // String[]{"Damage=15","Attack Speed=0.75"});
      // INVENTORY.addItem("Steel Scimitar", 500,1, "Sword_4.png","Meele",new
      // String[]{"Damage=50","Attack Speed=0.75"});
      // INVENTORY.addItem("Steel Katana", 450,1, "Sword_6.png","Meele",new
      // String[]{"Damage=40","Attack Speed=0.95"});
      // INVENTORY.addItem("Butcher's Sword", 5000,1, "Sword_3.png","Meele",new
      // String[]{"Damage=100","Attack Speed=0.55"});
      // INVENTORY.addItem("Blood Thirster", 6000,1, "Sword_8.png","Meele",new
      // String[]{"Damage=200","Attack Speed=0.75"});

      INVENTORY.addItem(
          "Iron Hammer",
          150,
          1,
          "Hammer_1.png",
          "Meele",
          new String[] {"Damage=40", "Attack Speed=0.15"});
      // INVENTORY.addItem("Steel Hammer", 450,1, "Hammer_0.png","Meele",new
      // String[]{"Damage=60","Attack Speed=0.15"});
      // INVENTORY.addItem("Iron Mace", 50,1, "Mace_1.png","Meele",new String[]{"Damage=15","Attack
      // Speed=0.5"});

      INVENTORY.addItem("Steel Helmet", 250, 1, "Head_1.png", "H_armor", new String[] {"Armor=20"});
      INVENTORY.addItem("Iron Helmet", 150, 1, "Head_2.png", "H_armor", new String[] {"Armor=5"});
      // INVENTORY.addItem("Iron Horn Helmet", 350,1, "Head_6.png","H_armor",new
      // String[]{"Armor=50","Magic Resist=0"});
      // INVENTORY.addItem("Steel Horn Helmet", 500,1, "Head_7.png","H_armor",new
      // String[]{"Armor=80","Magic Resist=0"});
      // INVENTORY.addItem("Skysteel Helmet", 4000,1, "Head_4.png","H_armor",new
      // String[]{"Armor=60","Magic Resist=25"});

      INVENTORY.addItem(
          "Iron Cuirass", 250, 1, "Chest_4.png", "C_armor", new String[] {"Armor=20"});
      INVENTORY.addItem(
          "Steel Cuirass", 350, 1, "Chest_1.png", "C_armor", new String[] {"Armor=30"});
      // INVENTORY.addItem("Scale Cuirass", 550,1, "Chest_3.png","C_armor",new
      // String[]{"Armor=50"});
      // INVENTORY.addItem("Dark metal Cuirass", 750,1, "Chest_6.png","C_armor",new
      // String[]{"Armor=70"});
      // INVENTORY.addItem("Master Cuirass", 3050,1, "Chest_5.png","C_armor",new
      // String[]{"Armor=80","Magic Resist=25"});
      // INVENTORY.addItem("Legendary Cuirass", 3050,1, "Chest_2.png","C_armor",new
      // String[]{"Armor=100","Magic Resist=100"});

      INVENTORY.addItem(
          "Wooden Shield",
          50,
          1,
          "Shield_1.png",
          "Shield",
          new String[] {"Armor=5", "Magic Resist=0"});

      // Add AI
      NAI = new NPCAI(this);

      // Identify as trader
      INVENTORY.Type = "Trader";

      // Set Stats
      STATS.setStats(new String[] {"Level = 5 "});
      MAX_HEALTH = 200;
      HEALTH = (int) MAX_HEALTH;
    } else if (CLASS.equals("Alchemist")) {
      // Add Items
      INVENTORY.addItem(
          "Health Potion", 25, 50, "Health Pot.png", "Potion", new String[] {"Points=50"});
      INVENTORY.addItem(
          "Mana Potion", 20, 50, "Mana Pot.png", "Potion", new String[] {"Points=50"});
      INVENTORY.addItem(
          "Speed Potion", 10, 50, "Speed Pot.png", "Potion", new String[] {"Points=5"});
      // INVENTORY.addItem("Invisib Potion", 50, 10, "Invisibility Pot.png","Potion",new
      // String[]{"Points=5"});

      // Add AI
      NAI = new NPCAI(this);

      // Identify as trader
      INVENTORY.Type = "Trader";
    } else if (CLASS.equals("Inn Keeper")) {
      // Add Items
      INVENTORY.addItem("Roasted Fish", 15, 10, "Fish.png", "Food", new String[] {"Points=5"});
      INVENTORY.addItem("Apple", 15, 10, "Apple.png", "Food", new String[] {"Points=2"});

      // Add AI
      NAI = new NPCAI(this);

      // Identify as trader
      INVENTORY.Type = "Trader";
    } else if (CLASS.equals("Mage")) {

      INVENTORY.addItem(
          "Leather Cap",
          250,
          1,
          "Head_8.png",
          "H_armor",
          new String[] {"Armor=5", "Magic Resist=25"});
      INVENTORY.addItem(
          "Dark Leather Cap",
          300,
          1,
          "Head_9.png",
          "H_armor",
          new String[] {"Armor=5", "Magic Resist=50"});
      // INVENTORY.addItem("Jesters Cap", 500,1, "Head_5.png","H_armor",new
      // String[]{"Armor=10","Magic Resist=90"});
      // INVENTORY.addItem("Skull Helmet", 5000,1, "Head_3.png","H_armor",new
      // String[]{"Armor=100","Magic Resist=100"});
      INVENTORY.addItem(
          "Shock Spell Stone",
          250,
          1,
          "Stone_1.png",
          "SpellStoner",
          new String[] {"Damage=" + SHOCK[0].STATS.DAMAGE});
      // INVENTORY.addItem("Darkness Spell Stone", 500,1, "Stone_1.png","SpellStoner",new
      // String[]{"Damage="+DARKNESS[0].STATS.DAMAGE});
      INVENTORY.addItem(
          "Life Drain Spell Stone",
          300,
          1,
          "Stone_1.png",
          "SpellStoner",
          new String[] {"Damage=" + LIFE_DRAIN[0].STATS.DAMAGE});

      // Add AI
      NAI = new NPCAI(this);

      // Identify as trader
      INVENTORY.Type = "Trader";

    } else if (CLASS.equals("Skeleton")) {

      // Add items
      INVENTORY.addItem(
          "Bone Club", 5, 1, "Mace_2.png", "Meele", new String[] {"Damage=5", "Attack Speed=1"});

      // Add Gold
      this.GOLD = (int) Math.round(Math.random() * 10 + 2);

      // Use Item
      INVENTORY.ItemEffect(0, this);

      // Add AI
      EAI = new EnemyAI(this);
    } else if (CLASS.equals("Skeleton Chieftan")) {

      // Add Item
      INVENTORY.addItem(
          "Iron Sword",
          50,
          1,
          "Sword_2.png",
          "Meele",
          new String[] {"Damage=15", "Attack Speed=0.65"});
      INVENTORY.addItem(
          "Health Potion", 25, 1, "Health Pot.png", "Potion", new String[] {"Points=50"});

      // Add Gold
      this.GOLD = (int) Math.round(Math.random() * 50 + 25);

      // Use Item
      INVENTORY.ItemEffect(0, this);

      // Assign Stats
      STATS.LEVEL = 3;
      HEALTH = 250;
      MAX_HEALTH = 250;

      // Opify
      Opify(1 / 1.25);

      // Add AI
      EAI = new EnemyAI(this);
    } else if (CLASS.equals("Shaman")) {

      // Add items
      INVENTORY.addItem(
          "Health Potion", 25, 1, "Health Pot.png", "Potion", new String[] {"Points=50"});

      // Add Ai
      NAI = new NPCAI(this);

    } else if (CLASS.equals("Dark Elf")) {

      // Add items
      INVENTORY.addItem(
          "Rusted Dagger",
          20,
          1,
          "Dagger_4.png",
          "Meele",
          new String[] {"Damage=10", "Attack Speed=1"});
      INVENTORY.addItem("Iron Helmet", 150, 1, "Head_2.png", "H_armor", new String[] {"Armor=5"});

      // Assign Stats
      STATS.LEVEL = 2;
      HEALTH = 150;
      MAX_HEALTH = 150;

      // Add Gold
      this.GOLD = (int) Math.round(Math.random() * 15 + 2);

      // Use Item
      INVENTORY.ItemEffect(0, this);
      INVENTORY.ItemEffect(1, this);

      // Add Ai
      EAI = new EnemyAI(this);

    } else if (CLASS.equals("Prisoner")) {
      INVENTORY.addItem("Key", 0, 1, "Key.png", "Key", new String[] {});
      // NAI= new NPCAI(this);
    }
  }

  /**
   * do damage to character
   *
   * @param Dmg Amount of Damage
   */
  public void Damage(int Dmg, int Type) {
    // If character is already dead then dont do damage
    if (ISDEAD) return;

    // Do damage
    if (Type == 1) {
      // DAMAGE FROM PHYSICAL ATTACK
      if (STATS.ARMOR > Dmg) return;
      HEALTH = HEALTH - Dmg + STATS.ARMOR;
    } else if (Type == 2) {
      // DAMAGE FROM MAGIC ATTACK
      if (STATS.MAGIC_RESIST > Dmg) return;
      HEALTH = HEALTH - Dmg + STATS.MAGIC_RESIST;
    }
    // If an Npc then run and hide
    if (NAI != null) {
      NAI.State = "alarmed";
    }

    // Death condition
    if (HEALTH <= 0) {
      // If player is dead
      if (this.CLASS.equals("Player")) {

        HEALTH = 0;

        // Quit game
        JOptionPane.showMessageDialog(null, "You are dead");
        X = 100;
        Y = 100;
        Opify(50);
        HEALTH = (int) MAX_HEALTH;

      } else {
        // If other character
        // set Death stats
        ISDEAD = true;
        HEALTH = 0;
        // display death
        CLASS = Cl + " (Dead)";

        // Rot effect
        for (int i = 0; i < imgCHARAC.getWidth(); i++) {
          for (int j = 0; j < imgCHARAC.getHeight(); j++) {
            imgCHARAC.setRGB(i, j, imgCHARAC.getRGB(i, j) * (int) Math.pow(3, 3));
          }
        }

        // Make inventory open to looting
        INVENTORY.OPEN_INVEN = true;
      }
    }
  }

  /** Prototype give player a leveled up look */
  public void Opify(double Fac) {

    for (int i = 0; i < imgCHARAC.getWidth(); i++) {
      for (int j = 0; j < imgCHARAC.getHeight(); j++) {
        if (imgCHARAC.getRGB(i, j) != imgCHARAC.getRGB(2, 2)) {
          imgCHARAC.setRGB(i, j, (int) Math.round(imgCHARAC.getRGB(i, j) * Fac));
        }
      }
    }
  }

  /**
   * Regenerate the players mana
   *
   * @param Mn amount to regen
   */
  public void ManaRegen(int Mn) {
    // Counter
    REGEN_COUNTER++;

    if (REGEN_COUNTER > 30) {
      // Regen
      if (MANA < MAX_MANA) MANA += Mn;
      REGEN_COUNTER = 0;
    }
  }

  /**
   * Move the character
   *
   * @param dx x displacement
   * @param dy y displacement
   */
  public void Move(int dx, int dy) {
    if (!CANMOVE) return;
    // Move
    X += dx * SPEED;
    Y += dy * SPEED;

    // Set FY depending on the sprite Type
    switch (TYPE) {
      case 1:
        if (dx > 0) {
          FY = Type1.RIGHT.ordinal();
        } else if (dx < 0) {
          FY = Type1.LEFT.ordinal();
        } else if (dy > 0) {
          FY = Type1.DOWN.ordinal();
        } else if (dy < 0) {
          FY = Type1.UP.ordinal();
        }

        break;
      case 2:
        if (dx > 0) {
          FY = Type2.RIGHT.ordinal();
        } else if (dx < 0) {
          FY = Type2.LEFT.ordinal();
        } else if (dy > 0) {
          FY = Type2.DOWN.ordinal();
        } else if (dy < 0) {
          FY = Type2.UP.ordinal();
        }
      case 3:
        if (dx > 0) {
          FY = Type3.RIGHT.ordinal();
        } else if (dx < 0) {
          FY = Type3.LEFT.ordinal();
        } else if (dy > 0) {
          FY = Type3.DOWN.ordinal();
        } else if (dy < 0) {
          FY = Type3.UP.ordinal();
        }

        break;
    }

    // X Frame Change
    FrameChange(SIZE, 4, 1);
  }

  /**
   * add a Map collision object
   *
   * @param M GridMap
   */
  public void addColisionObject(GridMap M) {
    MAP.add(M);
  }
  /**
   * add a Object collision object
   *
   * @param O Object
   */
  public void addColisionObject(GameObject O) {
    OBJECTS.add(O);
  }
  /**
   * add Character collision object
   *
   * @param C Character
   */
  public void addColisionObject(GameCharacter C) {
    CHARACTERS.add(C);
  }
  /**
   * add Building collision object
   *
   * @param B Building
   */
  public void addColisionObject(Building B) {
    BUILD.add(B);
  }

  /**
   * add an array of Building collision object
   *
   * @param M Array of GridMap
   */
  public void addColisionObject(Building[] B) {
    for (int i = 0; i < B.length; i++) {
      BUILD.add(B[i]);
    }
  }

  /**
   * add a Map collision object
   *
   * @param M Array of GridMap
   */
  public void addColisionObject(GridMap[] M) {
    for (int i = 0; i < M.length; i++) {
      MAP.add(M[i]);
    }
  }

  /**
   * add a Object collision object
   *
   * @param O Array of Objects
   */
  public void addColisionObject(GameObject[] O) {
    for (int i = 0; i < O.length; i++) {
      OBJECTS.add(O[i]);
    }
  }

  /** Remove all the collision objects from the player */
  public void removeCollisionObject(GameObject[] obj) {
    for (int i = 0; i < obj.length; i++) {
      OBJECTS.remove(obj[i]);
      // OBJECTS.add(obj[i]);
    }
  }

  public void removeCollisionObject(GameObject obj) {
    //	for(int i=0;i<obj.length;i++){
    OBJECTS.remove(obj);
    // OBJECTS.add(obj[i]);
    // }
  }

  public void removeAllColisionObjects() {
    // Collision maps
    MAP = new Vector<GridMap>();

    // Collision objects
    OBJECTS = new Vector<GameObject>();

    // Collision characters
    CHARACTERS = new Vector<GameCharacter>();

    // Collision characters
    BUILD = new Vector<Building>();
  }

  /**
   * add Character collision object
   *
   * @param C Array of Characters
   */
  public void addColisionObject(GameCharacter[] C) {
    for (int i = 0; i < C.length; i++) {
      CHARACTERS.add(C[i]);
    }
  }
  /**
   * Allows the character to walk over various surfaces
   *
   * @param F Selected fill number
   * @return whether or not the character can walk on this surface
   */
  public boolean isValidSurface(int F) {
    // List of valid surfaces
    int[] fill = {0, 98, 106, 107, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 147, 178};

    for (int i = 0; i < fill.length; i++) {
      if (fill[i] == F) {
        // If valid
        return true;
      }
    }

    // If not
    return false;
  }

  /**
   * Wall Collision
   *
   * @param x X Position
   * @param y Y Position
   * @param M Map
   * @return if character is about to collide with the wall
   */
  public boolean WallCollision(double x, double y, GridMap M) {
    // If invalid coordinate
    try {
      if (M.getBlockNum(x, y) == -1) {
        // Collision check
        if (isValidSurface(M.Fill[M.getBlockNum(x + 3, y + 3)])) {
          return false;
        }
        return true;
      }
      // Collision check
      if (isValidSurface(M.Fill[M.getBlockNum(x, y)])) {
        return false;
      }
    } catch (Exception e) {
      return WallCollision(x + M.Size / 2, y + M.Size / 2, M);
    }
    return true;
  }

  /**
   * Object Collision
   *
   * @param x X Position
   * @param y Y Position
   * @param Obj Game Object
   * @return if character is about to collide with an object
   */
  public boolean ObjectCollision(double x, double y, GameObject Obj) {
    if ((x > Obj.X) && (x < Obj.X + Obj.W * Obj.GROWTHFACTOR)) {
      if ((y > Obj.Y) && (y < Obj.Y + Obj.H * Obj.GROWTHFACTOR)) {
        return true;
      }
    }

    return false;
  }

  /**
   * Character Collision
   *
   * @param x X Position
   * @param y Y Position
   * @param Charac GameCharacter
   * @return if character is about to collide with a character
   */
  public boolean CharacterCollision(double x, double y, GameCharacter Charac) {
    if ((x > Charac.X) && (x < Charac.X + Charac.W * Charac.GROWTHFACTOR)) {
      if ((y > Charac.Y) && (y < Charac.Y + Charac.H * Charac.GROWTHFACTOR)) {

        return true;
      }
    }

    return false;
  }

  /**
   * Building Collision
   *
   * @param x X Position
   * @param y Y Position
   * @param Charac Game Building
   * @return if character is about to collide with a structure
   */
  public boolean BuildingCollision(double x, double y, Building Charac) {
    if ((x > Charac.X) && (x < Charac.X + Charac.W * Charac.GROWTHFACTOR)) {
      if ((y > Charac.Y) && (y < Charac.Y + Charac.H * Charac.GROWTHFACTOR)) {
        return true;
      }
    }

    return false;
  }

  /**
   * Check character collision with all kinds of objects
   *
   * @param x X Coordinate
   * @param y Y Coordinate
   * @return if Character is about to collide with something
   */
  public boolean Collision(double x, double y) {
    boolean blnCol = false;
    // Wall Collision
    for (int i = 0; i < MAP.size(); i++) {
      blnCol = blnCol || WallCollision(x, y, MAP.elementAt(i));
    }
    // Game Object Collision
    for (int i = 0; i < OBJECTS.size(); i++) {
      blnCol = blnCol || ObjectCollision(x, y, OBJECTS.elementAt(i));
    }
    // Game Character collision
    for (int i = 0; i < CHARACTERS.size(); i++) {
      blnCol = blnCol || CharacterCollision(x, y, CHARACTERS.elementAt(i));
    }
    // Game Building Collision
    for (int i = 0; i < BUILD.size(); i++) {
      blnCol = blnCol || BuildingCollision(x, y, BUILD.elementAt(i));
    }

    return blnCol;
  }

  /**
   * Draw character in minimap
   *
   * @param g Graphics
   * @param Dx X Displacement
   * @param Dy Y Displacement
   */
  public void MapDraw(Graphics g, int Dx, int Dy, double Scale, Color col) {
    // Color
    g.setColor(col.darker().darker().darker());
    g.drawOval((int) (X * Scale + Dx), (int) (Y * Scale + Dy), 7, 7);
    g.setColor(col);
    g.fillOval((int) (X * Scale + Dx), (int) (Y * Scale + Dy), 7, 7);
  }
  /**
   * Draw character in game window
   *
   * @param g Graphics
   * @param Dx X Displacement
   * @param Dy Y Displacement
   * @param G Growth factor
   */
  public void Draw(Graphics g, int Dx, int Dy, double G) {
    // Draw blood
    if (ISDEAD) {
      g.drawImage(
          imgBLOOD,
          (int) (X + Dx - 25),
          (int) (Y + Dy - 15),
          (int) (W * GROWTHFACTOR + 35),
          (int) (H * GROWTHFACTOR + 35),
          null);
    }

    // Quest Givers
    if (CLASS != "Player") {
      for (int i = 0; i < QUEST_LIST.size(); i++) {
        if (QUEST_LIST.elementAt(i).STATUS == 0) {
          g.drawImage(imgQStart, (int) (X + Dx + 5), (int) (Y + Dy - 30), (int) W, 35, null);
        } else if (QUEST_LIST.elementAt(i).STATUS == 2) {
          g.drawImage(imgQEnd, (int) (X + Dx), (int) (Y + Dy - 30), (int) W + 5, 35, null);
        }
      }
    }

    // Draw character
    g.drawImage(
        imgCHARAC,
        (int) (X + Dx),
        (int) (Y + Dy),
        (int) (X + Dx + W * G),
        (int) (Y + Dy + H * G),
        (int) (W * FX),
        (int) (H * FY),
        (int) (W * FX + W),
        (int) (H * FY + H),
        null);

    GROWTHFACTOR = G;
  }

  /**
   * Draw Magic Attack
   *
   * @param Magic Array of magic attacks
   * @param g Graphics
   * @param Dx Draw X displacement
   * @param Dy Draw Y displacement
   * @param G Growth Factor
   */
  public void MagicDraw(MagicAttack[] Magic, Graphics g, int Dx, int Dy, double G) {

    for (int i = 0; i < Magic.length; i++) {
      Magic[i].Draw(g, Dx, Dy, G);
    }
  }

  /** If the character is dead don't make the magic attacks collide */
  public void removeMagicCollision() {
    // Fireball
    for (int i = 0; i < FIREBALL.length; i++) {
      FIREBALL[i].removeAllColisionObjects();
    }

    // Shock
    for (int i = 0; i < SHOCK.length; i++) {
      SHOCK[i].removeAllColisionObjects();
    }

    // Darkness
    for (int i = 0; i < DARKNESS.length; i++) {
      DARKNESS[i].removeAllColisionObjects();
    }

    // Life Drain
    for (int i = 0; i < LIFE_DRAIN.length; i++) {
      LIFE_DRAIN[i].removeAllColisionObjects();
    }
  }

  /**
   * Frame Change in X direction
   *
   * @param MAX last frame index
   * @param Delay Delay between frame change
   * @param Dir moves back or forward through frames
   */
  public void FrameChange(int MAX, int Delay, int Dir) {
    COUNTER++;

    if (COUNTER > Delay) {
      // Change Frame
      FX += Dir;

      // Reset when frame number exceeds bounds
      if (FX < 0) {
        FX = MAX;
      }
      if (FX > MAX) {
        FX = 0;
      }

      // Reset
      COUNTER = 0;
    }
  }
  /**
   * Spawn a character on the map
   *
   * @param MiX Minimum X value
   * @param MiY Minimum Y value
   * @param MaX Maximum X value
   * @param MaY Maximum Y value
   */
  public void Spawn(int MiX, int MiY, int MaX, int MaY) {
    double Nx = 0, Ny = 0;

    // Random coordinate
    Nx = Math.random() * MaX + MiX;
    Ny = Math.random() * MaY + MiY;

    // Store block number
    int BNum = MAP.elementAt(0).getBlockNum(Nx + W / 2, Ny + H / 2);

    // if invalid block number
    if (BNum == -1) {
      Spawn(MiX, MiY, MaX, MaY);
    }

    // if invalid surface
    else if (!isValidSurface(MAP.elementAt(0).Fill[BNum])) {
      Spawn(MiX, MiY, MaX, MaY);
    }

    // if colliding with something
    else if (this.Collision(Nx + W / 2, Ny + H / 2)) {
      Spawn(MiX, MiY, MaX, MaY);
    } else {
      X = Nx;
      Y = Ny;
    }
  }
  /**
   * Find the distance between two characters
   *
   * @param Targ Target character
   * @return distance
   */
  public double Dist(GameCharacter Targ) {
    // find x squared and y squared
    double dx =
        Math.pow(((X + W / 2 * GROWTHFACTOR) - (Targ.X + Targ.W / 2 * Targ.GROWTHFACTOR)), 2);
    double dy =
        Math.pow(((Y + H / 2 * GROWTHFACTOR) - (Targ.Y + Targ.H / 2 * Targ.GROWTHFACTOR)), 2);

    // find distance
    return (Math.sqrt(dx + dy));
  }

  /**
   * Find the distance between two characters
   *
   * @param Targ Target character
   * @return distance
   */
  public double Dist(GameObject Targ) {
    // find x squared and y squared
    double dx =
        Math.pow(((X + W / 2 * GROWTHFACTOR) - (Targ.X + Targ.W / 2 * Targ.GROWTHFACTOR)), 2);
    double dy =
        Math.pow(((Y + H / 2 * GROWTHFACTOR) - (Targ.Y + Targ.H / 2 * Targ.GROWTHFACTOR)), 2);
    // find distance
    return (Math.sqrt(dx + dy));
  }
  /**
   * Find the distance between a character and a building
   *
   * @param Targ Target Building
   * @return distance
   */
  public double Dist(Building Targ) {

    // find x squared and y squared
    double dx =
        Math.pow(((X + W / 2 * GROWTHFACTOR) - (Targ.X + Targ.W / 2 * Targ.GROWTHFACTOR)), 2);
    double dy =
        Math.pow(((Y + H / 2 * GROWTHFACTOR) - (Targ.Y + Targ.H / 2 * Targ.GROWTHFACTOR)), 2);

    // find distance
    return (Math.sqrt(dx + dy));
  }

  /**
   * Chase another character
   *
   * @param Targ Target character
   * @param Error alignment error allowed
   */
  public void FollowChar(GameCharacter Targ, int Error) {

    // Find distance
    double dx = (Targ.X + Targ.W / 2 * Targ.GROWTHFACTOR) - (X + W / 2 * GROWTHFACTOR);
    double dy = (Targ.Y + Targ.H / 2 * Targ.GROWTHFACTOR) - (Y + H / 2 * GROWTHFACTOR);

    // Y Movement
    if (dy > Error) {
      // Down
      if (this.Collision(X, Y + H * GROWTHFACTOR)) {
        EAI.STATE = "calm";
      }
      Move(0, SPEED + 1);
    } else if (dy < Error) {
      // Up
      if (this.Collision(X, Y)) {
        EAI.STATE = "calm";
      }
      Move(0, -SPEED - 1);
    }

    // X Movement
    if (dx > Error) {
      // Right
      if (this.Collision(X + W * GROWTHFACTOR, Y)) {
        EAI.STATE = "calm";
      }
      Move(SPEED + 1, 0);
    } else if (dx < -Error) {
      // Left
      if (this.Collision(X, Y)) {
        EAI.STATE = "calm";
      }
      Move(-SPEED - 1, 0);
    }
  }

  /**
   * Set the direction of the character
   *
   * @param Pos String specifying direction
   */
  public void setPos(String Pos) {
    // Set position
    switch (TYPE) {
      case 1:
        switch (Pos) {
          case "Up":
            FY = Type1.UP.ordinal();
            break;
          case "Down":
            FY = Type1.DOWN.ordinal();
            break;
          case "Left":
            FY = Type1.LEFT.ordinal();
            break;
          case "Right":
            FY = Type1.RIGHT.ordinal();
            break;
        }
        break;
      case 2:
        switch (Pos) {
          case "Up":
            FY = Type2.UP.ordinal();
            break;
          case "Down":
            FY = Type2.DOWN.ordinal();
            break;
          case "Left":
            FY = Type2.LEFT.ordinal();
            break;
          case "Right":
            FY = Type2.RIGHT.ordinal();
            break;
        }
        break;
      case 3:
        switch (Pos) {
          case "Up":
            FY = Type3.UP.ordinal();
            break;
          case "Down":
            FY = Type3.DOWN.ordinal();
            break;
          case "Left":
            FY = Type3.LEFT.ordinal();
            break;
          case "Right":
            FY = Type3.RIGHT.ordinal();
            break;
        }
        break;
    }
  }
  /**
   * Sell an item to a shopkeeper
   *
   * @param Targ Target Inventory
   * @param Index Item Index
   */
  public void Sell(ItemList Targ, int Index) {
    // Un-equip item
    if (INVENTORY.ITEM_NAME.elementAt(Index).indexOf("<Eq>") != -1) {
      INVENTORY.ItemEffect(Index, this);
    }

    // Give the target this item
    Targ.addItem(
        this.INVENTORY.ITEM_NAME.elementAt(Index),
        this.INVENTORY.ITEM_PRICE.elementAt(Index),
        1,
        this.INVENTORY.ITEM_IMAGE.elementAt(Index),
        this.INVENTORY.ITEM_TAG.elementAt(Index),
        this.INVENTORY.STATS.elementAt(Index));

    // Get payment from target
    this.GOLD += this.INVENTORY.ITEM_PRICE.elementAt(Index);

    // Remove item from the character inventory
    this.INVENTORY.removeItem(Index, 1);
  }
  /**
   * Buy an item from a shopkeeper
   *
   * @param Targ Target Inventory
   * @param Index Item Index
   */
  public void Buy(ItemList Targ, int Index) {
    // If item is too expensive
    if (Targ.ITEM_PRICE.elementAt(Index) > this.GOLD) {
      JOptionPane.showMessageDialog(null, "Too rich for your blood");
      return;
    }

    // add Item to character inventory
    this.INVENTORY.addItem(
        Targ.ITEM_NAME.elementAt(Index),
        Targ.ITEM_PRICE.elementAt(Index),
        1,
        Targ.ITEM_IMAGE.elementAt(Index),
        Targ.ITEM_TAG.elementAt(Index),
        Targ.STATS.elementAt(Index));

    // remove Gold
    this.GOLD -= Targ.ITEM_PRICE.elementAt(Index);

    // remove item from target inventory
    Targ.removeItem(Index, 1);
  }
  /**
   * Loot item from a dead body
   *
   * @param Targ Target Inventory
   * @param Index Item Index
   */
  public void Take(ItemList Targ, int Index) {
    // Add item to character inventory

    // unequip item
    if (Targ.ITEM_NAME.elementAt(Index).indexOf("<Eq>") != -1) {
      Targ.ItemEffect(Index, this);
    }
    this.INVENTORY.addItem(
        Targ.ITEM_NAME.elementAt(Index),
        Targ.ITEM_PRICE.elementAt(Index),
        1,
        Targ.ITEM_IMAGE.elementAt(Index),
        Targ.ITEM_TAG.elementAt(Index),
        Targ.STATS.elementAt(Index));

    // Remove item from target inven
    Targ.removeItem(Index, 1);
  }

  /**
   * Magic Attack
   *
   * @param Magic Array of magic attacks
   */
  public void MAttack(MagicAttack[] Magic) {
    // If insufficient mana
    if (MANA - Magic[MAGIC_COUNTER].STATS.POINTS < 0) return;
    // Stop
    FIREBALL[MAGIC_COUNTER].ISACTIVE = false;

    switch (TYPE) {
      case 1:
        // set x and y coords depending on the direction the character is facing
        switch (FY) {
          case 0: // Down
            // Set x and y coords
            Magic[MAGIC_COUNTER].X =
                X + W / 2 - Magic[MAGIC_COUNTER].W / 2 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            Magic[MAGIC_COUNTER].Y =
                Y + H - Magic[MAGIC_COUNTER].H / 4 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            // Set frame 0
            Magic[MAGIC_COUNTER].FX = 0;
            // Movement Speed
            Magic[MAGIC_COUNTER].dX = 0;
            Magic[MAGIC_COUNTER].dY = 20;
            break;

          case 1: // Left
            // Set x and y coords
            Magic[MAGIC_COUNTER].X =
                X - Magic[MAGIC_COUNTER].W / 4 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            Magic[MAGIC_COUNTER].Y =
                Y + H / 2 - Magic[MAGIC_COUNTER].H / 2 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            // Set frame 0
            Magic[MAGIC_COUNTER].FX = 0;
            // Movement Speed
            Magic[MAGIC_COUNTER].dX = -20;
            Magic[MAGIC_COUNTER].dY = 0;
            break;

          case 2: // Right
            // Set x and y coords
            Magic[MAGIC_COUNTER].X =
                X + W - Magic[MAGIC_COUNTER].W / 4 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            Magic[MAGIC_COUNTER].Y =
                Y + H / 2 - Magic[MAGIC_COUNTER].H / 2 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            // Set frame 0
            Magic[MAGIC_COUNTER].FX = 0;
            // Movement Speed
            Magic[MAGIC_COUNTER].dX = 20;
            Magic[MAGIC_COUNTER].dY = 0;
            break;

          case 3: // Up
            // Set x and y coords
            Magic[MAGIC_COUNTER].X =
                X + W / 2 - Magic[MAGIC_COUNTER].W / 2 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            Magic[MAGIC_COUNTER].Y =
                Y - Magic[MAGIC_COUNTER].H / 2 * Magic[MAGIC_COUNTER].GROWTHFACTOR;
            // Set frame 0
            Magic[MAGIC_COUNTER].FX = 0;
            // Movement Speed
            Magic[MAGIC_COUNTER].dX = 0;
            Magic[MAGIC_COUNTER].dY = -20;
            break;
        }
    }
    // Activate
    Magic[MAGIC_COUNTER].ISACTIVE = true;

    // Consume mana
    MANA -= Magic[MAGIC_COUNTER].STATS.POINTS;

    // Change counter
    MAGIC_COUNTER++;
    if (MAGIC_COUNTER == Magic.length) MAGIC_COUNTER = 0;
  }

  /**
   * Physical Meele Attack
   *
   * @param Me
   */
  public void PAttack(MeeleAttack Me) {

    switch (TYPE) {
      case 1:
        // Meele Attack
        if (FY == Type1.UP.ordinal()) {
          Me.PAttack(Type1.UP.name());
        } else if (FY == Type1.DOWN.ordinal()) {
          Me.PAttack(Type1.DOWN.name());
        } else if (FY == Type1.LEFT.ordinal()) {
          Me.PAttack(Type1.LEFT.name());
        } else if (FY == Type1.RIGHT.ordinal()) {
          Me.PAttack(Type1.RIGHT.name());
        }

        break;
      case 2:
        // Meele Attack
        if (FY == Type2.UP.ordinal()) {
          Me.PAttack(Type2.UP.name());
        } else if (FY == Type2.DOWN.ordinal()) {
          Me.PAttack(Type2.DOWN.name());
        } else if (FY == Type2.LEFT.ordinal()) {
          Me.PAttack(Type2.LEFT.name());
        } else if (FY == Type2.RIGHT.ordinal()) {
          Me.PAttack(Type2.RIGHT.name());
        }

        break;
      case 3:
        // Meele Attack
        if (FY == Type3.UP.ordinal()) {
          Me.PAttack(Type3.UP.name());
        } else if (FY == Type3.DOWN.ordinal()) {
          Me.PAttack(Type3.DOWN.name());
        } else if (FY == Type3.LEFT.ordinal()) {
          Me.PAttack(Type3.LEFT.name());
        } else if (FY == Type3.RIGHT.ordinal()) {
          Me.PAttack(Type3.RIGHT.name());
        }

        break;
    }
  }

  /**
   * get xp and gold from killing characters
   *
   * @param Charac collision characters
   */
  public void KillXP(GameCharacter Charac) {
    // When the character dies
    if (Charac.ISDEAD && Charac.COLL_LISTENER) {

      Charac.COLL_LISTENER = false;
      audDEATH.playAudio("death.wav");

      // Remove collision listener
      for (int j = 0; j < FIREBALL.length; j++) {
        FIREBALL[j].removeCollChar(Charac);
      }
      for (int j = 0; j < SHOCK.length; j++) {
        SHOCK[j].removeCollChar(Charac);
      }
      for (int j = 0; j < DARKNESS.length; j++) {
        DARKNESS[j].removeCollChar(Charac);
      }
      for (int j = 0; j < LIFE_DRAIN.length; j++) {
        LIFE_DRAIN[j].removeCollChar(Charac);
      }

      // Add Xp
      STATS.IncreaseXP(10 * Charac.STATS.LEVEL);
      // Add Gold
      this.GOLD += Charac.GOLD;
    }
  }

  /**
   * get xp and gold from killing characters
   *
   * @param Charac collision characters
   */
  public void KillXP(GameCharacter[] Charac) {
    // When the character dies
    for (int i = 0; i < Charac.length; i++) {
      if (Charac[i].ISDEAD && Charac[i].COLL_LISTENER) {

        Charac[i].COLL_LISTENER = false;
        audDEATH.playAudio("death.wav");

        // Remove collision listener
        for (int j = 0; j < FIREBALL.length; j++) {
          FIREBALL[j].removeCollChar(Charac[i]);
        }
        for (int j = 0; j < SHOCK.length; j++) {
          SHOCK[j].removeCollChar(Charac[i]);
        }
        for (int j = 0; j < DARKNESS.length; j++) {
          DARKNESS[j].removeCollChar(Charac[i]);
        }
        for (int j = 0; j < LIFE_DRAIN.length; j++) {
          LIFE_DRAIN[j].removeCollChar(Charac[i]);
        }

        // Add Xp
        STATS.IncreaseXP(10 * Charac[i].STATS.LEVEL);
        // Add Gold
        this.GOLD += Charac[i].GOLD;
      }
    }
  }

  /**
   * Check if this x and y coordinate is within the component
   *
   * @param x X coordinate
   * @param y Y coordinate
   */
  public boolean Contains(double x, double y) {
    // Check collision
    if ((x > X) && (x < X + W * GROWTHFACTOR)) {
      if ((y > Y) && (y < Y + H * GROWTHFACTOR)) {
        return true;
      }
    }

    return false;
  }

  /**
   * Used for debugging get list of spells available to character
   *
   * @return List
   */
  public String[] getSpellList() {
    // Make Array
    String[] arg = new String[SPELL_LIST.size()];

    // Assign names
    for (int i = 0; i < arg.length; i++) {
      arg[i] = SPELL_LIST.elementAt(i)[0].NAME;
      System.out.println(arg[i]);
    }

    // Return list
    return arg;
  }

  /**
   * Spells collide with the given characters
   *
   * @param Charac Game character array
   */
  public void addMagicCharacCollision(GameCharacter[] Charac) {

    // FIREBALL
    for (int i = 0; i < FIREBALL.length; i++) {
      FIREBALL[i].addCollChar(Charac);
    }

    // SHOCK
    for (int i = 0; i < SHOCK.length; i++) {
      SHOCK[i].addCollChar(Charac);
    }

    // DARKNESS
    for (int i = 0; i < DARKNESS.length; i++) {
      DARKNESS[i].addCollChar(Charac);
    }

    // LIFE DRAIN
    for (int i = 0; i < LIFE_DRAIN.length; i++) {
      LIFE_DRAIN[i].addCollChar(Charac);
    }
  }

  /**
   * Spells collide with the given characters
   *
   * @param Charac Game character array
   */
  public void addMagicCharacCollision(GameCharacter Charac) {

    // FIREBALL
    for (int i = 0; i < FIREBALL.length; i++) {
      FIREBALL[i].addCollChar(Charac);
    }

    // SHOCK
    for (int i = 0; i < SHOCK.length; i++) {
      SHOCK[i].addCollChar(Charac);
    }

    // DARKNESS
    for (int i = 0; i < DARKNESS.length; i++) {
      DARKNESS[i].addCollChar(Charac);
    }

    // LIFE DRAIN
    for (int i = 0; i < LIFE_DRAIN.length; i++) {
      LIFE_DRAIN[i].addCollChar(Charac);
    }
  }

  /**
   * Spells collide with walls
   *
   * @param Map GridMap
   */
  public void addMagicMapCollision(GridMap Map) {

    // FIREBALL
    for (int i = 0; i < FIREBALL.length; i++) {
      FIREBALL[i].addColisionObject(Map);
    }

    // SHOCK
    for (int i = 0; i < SHOCK.length; i++) {
      SHOCK[i].addColisionObject(Map);
    }

    // DARKNESS
    for (int i = 0; i < DARKNESS.length; i++) {
      // DARKNESS[i].addColisionObject(Map);
    }

    // LIFE DRAIN
    for (int i = 0; i < LIFE_DRAIN.length; i++) {
      LIFE_DRAIN[i].addColisionObject(Map);
    }
  }

  public void Heal(int Amount) {
    HEALTH += Amount;
    if (HEALTH > MAX_HEALTH) HEALTH = (int) MAX_HEALTH;
  }

  public void giveQuest(GameCharacter Reciever) {
    if (QUEST_LIST.size() > 0) {
      if (QUEST_LIST.elementAt(0).STATUS == 0) {
        Reciever.QUEST_LIST.add(QUEST_LIST.elementAt(0));
        QUEST_LIST.elementAt(0).play_UpdateSound();
        if (QUEST_LIST.elementAt(0).QTYPE == Quest_Type.DELIVERY) {
          for (int i = 0; i < QUEST_LIST.elementAt(0).TARGET_LIST.ITEM_NAME.size(); i++) {
            Reciever.INVENTORY.addItem(
                QUEST_LIST.elementAt(0).TARGET_LIST.ITEM_NAME.elementAt(i),
                QUEST_LIST.elementAt(0).TARGET_LIST.ITEM_PRICE.elementAt(i),
                QUEST_LIST.elementAt(0).TARGET_LIST.ITEM_QUANTITY.elementAt(i),
                QUEST_LIST.elementAt(0).TARGET_LIST.ITEM_IMAGE.elementAt(i),
                QUEST_LIST.elementAt(0).TARGET_LIST.ITEM_TAG.elementAt(i),
                QUEST_LIST.elementAt(0).TARGET_LIST.STATS.elementAt(i));
          }
        }
        QUEST_LIST.elementAt(0).STATUS = 1;
      }
    }
  }

  public void CompleteQuest(int Index) {
    Quest qstComp = QUEST_LIST.elementAt(Index);
    qstComp.STATUS = 3;
    qstComp.QUEST_GIVER.QUEST_LIST.elementAt(0).STATUS = 3;
    qstComp.QUEST_GIVER.QUEST_LIST.removeElementAt(0);
    STATS.IncreaseXP(qstComp.XP);
    GOLD += qstComp.GOLD;
  }

  public BufferedImage getImage(String Direct, String FName) {
    // JOptionPane.showMessageDialog(null, "GameCharacter");
    try {
      BufferedImage bg = ImageIO.read(getClass().getResource(Direct + FName));
      return bg;

    } catch (Exception e) {
      JOptionPane.showMessageDialog(null, getClass().toString());
    }
    return null;
  }

  public boolean isJar() {
    Path pth = Paths.get(System.getProperty("user.dir") + "/Advent.jar");

    if (pth.toFile().exists()) return true;
    return false;
  }
}
  public boolean isJar() {
    Path pth = Paths.get(System.getProperty("user.dir") + "/Advent.jar");

    if (pth.toFile().exists()) return true;
    return false;
  }
Exemple #5
0
/**
 * a View for rendering Text's based on bitmaps (when available) or TextLayout (when image not
 * available)
 */
public class TextViewHybrid extends LeafElementView implements Runnable {

  boolean wantToComputeLatexDimensions =
      true; // from preferences: do we want to run LateX to compute preferences
  boolean wantToGetBitMap =
      true; // from preferences: do we want to run LateX+pstoimg to get a bitmap.
  //   wantToGetBitMap=true should Imply wantToComputeLatexDimensions=true

  protected double strx, stry; // TextLayout/Image location with respect to PicText's anchor point
  // [pending] pas joli. A enlever sous peu (utilise juste dans HitInfo que je ne comprends pas, je
  // laisse donc en attendant)

  protected TextLayout
      textLayout; // the TextLayout that renders the text string of this TextEditable
  // [inherited] shape; But here it's the frame box !!! (not textLayout !)
  protected AffineTransform text2ModelTr =
      new AffineTransform();; // maps text coordinates to Model coordinates
  protected BufferedImage image; // bitmap (if null, we rely on TextLayout)
  protected boolean areDimensionsComputed; // has the real dimensions been read from the log file ?
  protected int fileDPI =
      300; // Dot Per Inch of the file (for image resizing) [pending] gerer les preferences de ce
           // parametre
  // il faut passer la valeur en DPI en argument a create_bitmap.sh

  /** pattern used for parsing log file */
  private static final Pattern LogFilePattern =
      Pattern.compile("JPICEDT INFO:\\s*([0-9.]*)pt,\\s*([0-9.]*)pt,\\s*([0-9.]*)pt");

  private static final String CR_LF = System.getProperty("line.separator");

  private PicPoint ptBuf = new PicPoint();

  /** construct a new View for the given PicRectangle */
  public TextViewHybrid(PicText te, AttributesViewFactory f) {
    super(te, f);
    areDimensionsComputed = false;
    changedUpdate(null);
  }

  public PicText getElement() {
    return (PicText) element;
  }

  /**
   * Returns the text rotation in radians : subclassers that don't support rotating text may return
   * 0 here. Used by TextLayout only.
   */
  protected double getRotation() {
    //			debug(set.getAttribute(TEXT_ROTATION).toString());
    return Math.toRadians(element.getAttribute(TEXT_ROTATION).doubleValue());
  }

  /**
   * Give notification from the model that a change occured to the text this view is responsible for
   * rendering.
   *
   * <p>
   */
  public void changedUpdate(DrawingEvent.EventType eventType) {
    PicText text = (PicText) element;
    if (textLayout == null) {
      // new *************************** begin (by ss & bp)
      textLayout =
          new TextLayout(
              text.getText(text.getTextMode()).length() == 0
                  ? " "
                  : text.getText(text.getTextMode()),
              // new *************************** end (by ss & bp)
              DefaultViewFactory.textFont, // static field
              new FontRenderContext(null, false, false));
    }
    if (eventType == DrawingEvent.EventType.TEXT_CHANGE) {
      // new *************************** begin (by ss & bp)
      textLayout =
          new TextLayout(
              text.getText(text.getTextMode()).length() == 0
                  ? " "
                  : text.getText(text.getTextMode()),
              // new *************************** end (by ss & bp)
              DefaultViewFactory.textFont,
              new FontRenderContext(null, false, false));

      // first try to create a bitmap
      image =
          null; // aka "reset" image => we might temporarily resort to TextLayout until the image is
                // ready
      areDimensionsComputed = false;
      // reset dimensions to the textlayout dimensions
      text.setDimensions(
          textLayout.getBounds().getWidth(), textLayout.getAscent(), textLayout.getDescent());

      // new *************************** begin (by ss & bp)
      if (wantToComputeLatexDimensions && text.getText(text.getTextMode()).length() > 0) {
        // new *************************** end (by ss & bp)
        // don't produce a bitmap for an empty string (LaTeX might not like it)
        // [pending] this should be made dependent on a preference's option
        new Thread(this).start();
      }
      if (image == null) super.changedUpdate(null); // ie resort to TextLayout (update all)
    } else {
      text.updateFrame();
      super.changedUpdate(eventType);
    }
  }

  // Thread's run method aimed at creating a bitmap asynchronously
  public void run() {
    Drawing drawing = new Drawing();
    PicText rawPicText = new PicText();
    String s = ((PicText) element).getText();
    rawPicText.setText(s);
    drawing.add(
        rawPicText); // bug fix: we must add a CLONE of the PicText, otherwise it loses it former
                     // parent... (then pb with the view )
    drawing.setNotparsedCommands(
        "\\newlength{\\jpicwidth}\\settowidth{\\jpicwidth}{"
            + s
            + "}"
            + CR_LF
            + "\\newlength{\\jpicheight}\\settoheight{\\jpicheight}{"
            + s
            + "}"
            + CR_LF
            + "\\newlength{\\jpicdepth}\\settodepth{\\jpicdepth}{"
            + s
            + "}"
            + CR_LF
            + "\\typeout{JPICEDT INFO: \\the\\jpicwidth, \\the\\jpicheight,  \\the\\jpicdepth }"
            + CR_LF);
    RunExternalCommand.Command commandToRun = RunExternalCommand.Command.BITMAP_CREATION;
    // RunExternalCommand command = new RunExternalCommand(drawing, contentType,commandToRun);
    boolean isWriteTmpTeXfile = true;
    String bitmapExt = "png"; // [pending] preferences
    String cmdLine =
        "{i}/unix/tetex/create_bitmap.sh {p} {f} "
            + bitmapExt
            + " "
            + fileDPI; // [pending] preferences
    ContentType contentType = getContainer().getContentType();
    RunExternalCommand.isGUI = false; // System.out, no dialog box // [pending] debug
    RunExternalCommand command =
        new RunExternalCommand(drawing, contentType, cmdLine, isWriteTmpTeXfile);
    command
        .run(); // synchronous in an async. thread => it's ok (anyway, we must way until the LaTeX
                // process has completed)

    if (wantToComputeLatexDimensions) {
      // load size of text:
      try {
        File logFile = new File(command.getTmpPath(), command.getTmpFilePrefix() + ".log");
        BufferedReader reader = null;
        try {
          reader = new BufferedReader(new FileReader(logFile));
        } catch (FileNotFoundException fnfe) {
          System.out.println("Cannot find log file! " + fnfe.getMessage());
          System.out.println(logFile);
        } catch (IOException ioex) {
          System.out.println("Log file IO exception");
          ioex.printStackTrace();
        } // utile ?
        System.out.println("Log file created! file=" + logFile);
        getDimensionsFromLogFile(reader, (PicText) element);
        syncStringLocation(); // update dimensions
        syncBounds();
        syncFrame();
        SwingUtilities.invokeLater(
            new Thread() {
              public void run() {
                repaint(null);
              }
            });
        // repaint(null); // now that dimensions are available, we force a repaint() [pending]
        // smart-repaint ?
      } catch (Exception e) {
        e.printStackTrace();
      }
    }

    if (wantToGetBitMap) {
      // load image:
      try {
        File bitmapFile =
            new File(command.getTmpPath(), command.getTmpFilePrefix() + "." + bitmapExt);
        this.image = ImageIO.read(bitmapFile);
        System.out.println(
            "Bitmap created! file="
                + bitmapFile
                + ", width="
                + image.getWidth()
                + "pixels, height="
                + image.getHeight()
                + "pixels");
        if (image == null) return;
        syncStringLocation(); // sets strx, stry, and dimensions of text
        syncBounds();
        // update the AffineTransform that will be applied to the bitmap before displaying on screen
        PicText te = (PicText) element;
        text2ModelTr.setToIdentity(); // reset
        PicPoint anchor = te.getCtrlPt(TextEditable.P_ANCHOR, ptBuf);
        text2ModelTr.rotate(getRotation(), anchor.x, anchor.y); // rotate along P_ANCHOR !
        text2ModelTr.translate(te.getLeftX(), te.getTopY());
        text2ModelTr.scale(
            te.getWidth() / image.getWidth(),
            -(te.getHeight() + te.getDepth()) / image.getHeight());
        // [pending]  should do something special to avoid dividing by 0 or setting a rescaling
        // factor to 0 [non invertible matrix] (java will throw an exception)
        syncFrame();
        SwingUtilities.invokeLater(
            new Thread() {
              public void run() {
                repaint(null);
              }
            });
        // repaint(null); // now that bitmap is available, we force a repaint() [pending]
        // smart-repaint ?
      } catch (Exception e) {
        e.printStackTrace();
      }
    }
  }

  /**
   * update strx stry = location of TextLayout's bottom-Left corner with respect to PicText's
   * anchor-point
   */
  protected void syncStringLocation() {
    PicText te = (PicText) element;
    PicPoint anchor = te.getCtrlPt(TextEditable.P_ANCHOR, ptBuf);
    if (image == null) {
      if (!areDimensionsComputed) {
        te.setDimensions(
            textLayout.getBounds().getWidth(), textLayout.getAscent(), textLayout.getDescent());
      }
      strx = te.getLeftX() - anchor.x;
      stry = te.getBaseLineY() - anchor.y;
    } else { // image not null
      strx = te.getLeftX() - anchor.x;
      stry = te.getBottomY() - anchor.y;
    }
  }

  /**
   * Synchronize the textLayout and the shape (=frame box, by calling syncFrame) with the model When
   * <code>TextLayout</code> is used, this delegates to <code>getRotation()</code> where computing
   * rotation angle is concerned, and updates the AffineTransform returned by <code>
   * getTextToModelTransform()</code>.
   */
  protected void syncShape() {
    PicText te = (PicText) element;

    //			textLayout = new TextLayout(te.getText().length()==0 ? " " : te.getText(),
    //			    textFont,
    //			    new FontRenderContext(null,false,false));

    text2ModelTr.setToIdentity(); // reset
    PicPoint anchor = te.getCtrlPt(TextEditable.P_ANCHOR, ptBuf);
    text2ModelTr.rotate(getRotation(), anchor.x, anchor.y); // rotate along P_ANCHOR !
    // the reference point of an image is the top-left one, but the refpoint of a text layout is on
    // the baseline
    if (image != null) {
      text2ModelTr.translate(te.getLeftX(), te.getTopY());
      if (te.getWidth() != 0
          && image.getWidth() != 0
          && (te.getDepth() + te.getHeight()) != 0
          && image.getHeight() != 0)
        text2ModelTr.scale(
            te.getWidth() / image.getWidth(),
            -(te.getHeight() + te.getDepth()) / image.getHeight());
    } else {
      // Hack ? Just cheating a little bit ? Ou juste ruse ?
      // we want here to use the dimensions of the textLayout instead of latex dimensions if
      // areDimensionsComputed
      // sinon on va aligner le textlayout en fonction des parametres latex, et l'Utilisateur (qui
      // est bien bete) ne va rien comprendre.
      double latexH = 0;
      double latexD = 0;
      double latexW = 0;
      if (areDimensionsComputed) { // store latex dimensions, and setDimensions to textLayout ones
        latexH = te.getHeight();
        latexD = te.getDepth();
        latexW = te.getWidth();
        te.setDimensions(
            textLayout.getBounds().getWidth(), textLayout.getAscent(), textLayout.getDescent());
      }
      text2ModelTr.translate(te.getLeftX(), te.getBaseLineY());
      if (areDimensionsComputed) { // restore latex dimensions
        te.setDimensions(latexW, latexH, latexD);
      }
      // Autre possibilite= comprimer le texte pour qu'il rentre dans la boite (evite le hack
      // ci-dessus):
      // text2ModelTr.scale(te.getWidth()/textLayout.getWidth(),-(te.getHeight()+te.getDepth())/textLayout.getHeight());
      text2ModelTr.scale(1.0, -1.0);
    }
    syncFrame();
  }

  /**
   * synchronize frame shape and location (TextLayout only) ; this is called by syncShape(), so that
   * subclasser might override easily when only rectangular shapes are availables.
   */
  protected void syncFrame() {
    PicText te = (PicText) element;
    if (!te.isFramed()) {
      return;
    }
    AffineTransform tr =
        new AffineTransform(); // maps Image coordinates to Model coordinates (see paint)
    tr.setToIdentity(); // reset
    PicPoint anchor = te.getCtrlPt(TextEditable.P_ANCHOR, ptBuf);
    tr.rotate(getRotation(), anchor.x, anchor.y); // rotate along P_ANCHOR !
    shape = tr.createTransformedShape(te.getShapeOfFrame());
  }

  protected void getDimensionsFromLogFile(BufferedReader reader, PicText text) {
    if (reader == null) {
      return;
    }
    String line = ""; // il rale si j'initialise pas ...
    boolean finished = false;
    while (!finished) {
      try {
        line = reader.readLine();
      } catch (IOException ioex) {
        ioex.printStackTrace();
        return;
      }
      if (line == null) {
        System.out.println("Size of text not found in log file...");
        return;
      }

      System.out.println(line);
      Matcher matcher = LogFilePattern.matcher(line);

      if (line != null && matcher.find()) {
        System.out.println("FOUND :" + line);
        finished = true;
        try {
          text.setDimensions(
              0.3515 * Double.parseDouble(matcher.group(1)), // height, pt->mm (1pt=0.3515 mm)
              0.3515 * Double.parseDouble(matcher.group(2)), // width
              0.3515 * Double.parseDouble(matcher.group(3))); // depth
          areDimensionsComputed = true;
        } catch (NumberFormatException e) {
          System.out.println("Logfile number format problem: $line" + e.getMessage());
        } catch (IndexOutOfBoundsException e) {
          System.out.println("Logfile regexp problem: $line" + e.getMessage());
        }
      }
    }
    return;
  }

  /** Synchronizes bounding box with the model ; */
  protected void syncBounds() {
    PicText te = (PicText) element;
    // [pending] Il faut tenir compte de la rotation !

    Rectangle2D latexBB =
        null; // BB relative to latex dimensions (including rotation) (without frame)
    Rectangle2D textLayoutBB =
        null; // BB relative to textLayout dimensions (including rotation) (without frame)
    Rectangle2D textBB = null; // BB of the text (including rotation), without frame

    if (areDimensionsComputed) { // compute latexBB
      Rectangle2D nonRotated =
          new Rectangle2D.Double(
              te.getLeftX(), te.getBottomY(), te.getWidth(), te.getHeight() + te.getDepth());
      AffineTransform tr =
          new AffineTransform(); // maps Image coordinates to Model coordinates (see paint)
      tr.setToIdentity(); // reset
      PicPoint anchor = te.getCtrlPt(TextEditable.P_ANCHOR, ptBuf);
      tr.rotate(getRotation(), anchor.x, anchor.y); // rotate along P_ANCHOR !
      latexBB = tr.createTransformedShape(nonRotated).getBounds2D();
    }

    if (image == null) { // compute textLayoutBB
      Rectangle2D nonRotated = textLayout.getBounds();
      textLayoutBB = text2ModelTr.createTransformedShape(nonRotated).getBounds2D();
    }

    // use textLayoutBB or latexBB or their union
    if (image != null) textBB = latexBB;
    else {
      if (!areDimensionsComputed) textBB = textLayoutBB;
      else {
        textBB = latexBB.createUnion(textLayoutBB);
      }
    }

    // union with frame BB
    if (te.isFramed()) {
      super.syncBounds(); // update bounds of the frame if necessary
      Rectangle2D.union(super.bounds, textBB, this.bounds);
    } else this.bounds = textBB;
  }

  /**
   * Render the View to the given graphic context. This implementation render the interior first,
   * then the outline.
   */
  public void paint(Graphics2D g, Rectangle2D a) {
    if (!a.intersects(getBounds())) return;
    if (image != null) { // paint bitmap
      g.drawImage(image, text2ModelTr, null);
      // debug:
      g.setPaint(Color.red);
      g.draw(this.bounds);
      super.paint(g, a); // possibly paint framebox if non-null
    } else { // paint textlayout
      super.paint(g, a); // possibly paint framebox if non-null

      AffineTransform oldAT = g.getTransform();
      // paint text in black
      g.setPaint(Color.black);
      // from now on, we work in Y-direct (<0) coordinates to avoid inextricable problems with font
      // being mirrored...
      g.transform(text2ModelTr); // also include rotation
      textLayout.draw(g, 0.0f, 0.0f);
      // [pending] ajouter un cadre si areDimensionsComputed (wysiwyg du pauvre)
      // get back to previous transform
      g.setTransform(oldAT);
      if (DEBUG) {
        g.setPaint(Color.red);
        g.draw(bounds);
      }
    }
  }

  /**
   * This implementation calls <code>super.hitTest</code> and returns the result if non-null (this
   * should be a HitInfo.Point), then returns a HitInfo.Interior if the mouse-click occured inside
   * the text bound (as defined by text layout)
   *
   * @return a HitInfo corresponding to the given mouse-event
   */
  public HitInfo hitTest(PEMouseEvent e) {

    // from Bitmap:
    if (image != null) {
      if (getBounds().contains(e.getPicPoint())) {
        return new HitInfo.Interior((PicText) element, e);
      }
      return null;
    }

    // from TextLayout:
    if (!getBounds().contains(e.getPicPoint())) return null;

    PicText te = (PicText) element;
    // recompute textlayout b-box, but store it in a temporary field !
    Rectangle2D tb = textLayout.getBounds();
    Shape text_bounds = text2ModelTr.createTransformedShape(tb);
    if (text_bounds.contains(e.getPicPoint())) {
      // [SR:pending] for the hitInfo to be reliable, getPicPoint() should first be transformed by
      //              inverse text2ModelTr ! (especially when rotationAngle != 0)
      TextHitInfo thi =
          textLayout.hitTestChar(
              (float) (e.getPicPoint().x - strx),
              (float) (e.getPicPoint().y - stry)); // guaranteed to return a non-null thi
      return new HitInfo.Text((PicText) element, thi, e);
    }
    // test hit on textlayout's bounding rectangle :
    // else if (bounds.contains(e.getPicPoint())) return new HitInfo.Interior(element,e);
    return null;
  }

  /**
   * [SR:pending] make this view implement aka TextEditableView interface (or something like it),
   * where TextEditableView is a subinterface of View with text-editing specific capabilities.
   *
   * <p>Returns the TextLayout which is responsible for painting the textual content of this element
   */
  public TextLayout getTextLayout() {
    return textLayout;
  }

  /**
   * Return an affine transform which translat b/w the TextLayout coordinate system and the
   * jpicedt.graphic.model coordinate system. [SR:pending] refactor method name to something more
   * explanatory
   */
  public AffineTransform getTextToModelTransform() {
    return text2ModelTr;
  }
} // TextView
Exemple #6
0
 public browse_jsp() {
   myUtil = new ewebeditor.server.util();
   sFileSeparator = System.getProperty("file.separator");
 }