/** * Este método calcula la distancia manhattan de la pos de este agente y de otro agente pasandolo * como Csight * * @param position * @param sight * @return */ protected double distanciaManhattan(Vector3D position, CSight sight) { // la clase CSight tiene un método getDistance(), preguntar que distancia es esa? double distancia = Math.abs(position.x - sight.getPosition().x) + Math.abs(position.y - sight.getPosition().y) + Math.abs(position.z - sight.getPosition().z); return distancia; }
/** * Calculates an array of positions for patrolling. * * <p>When this method is called, it creates an array of <tt> n</tt> random positions. For medics * and fieldops, the rank of <tt> n</tt> is [1..1]. For soldiers, the rank of <tt> n</tt> is * [5..10]. * * <p><em> It's very useful to overload this method. </em> */ protected void CreateControlPoints() { int iMaxCP = 0; switch (m_eClass) { case CLASS_MEDIC: case CLASS_FIELDOPS: super.CreateControlPoints(); break; case CLASS_SOLDIER: // aqui tengo que cambiar posBandera por posBaseAllied // m_Map.getClass().getField(m_sMedicService) // CTerrainMap.this.getClass().getField(name) // m_AlliedBase no la reconoce la variable int xini = (int) (posBandera.x) / 8; int zini = (int) (posBandera.z) / 8; int x = xini; int z = zini; while (z < 32 && x > 0 && (Math.abs(x - xini) <= 3) && m_Map.CanWalk(x - 1, z + 1)) { x--; z++; } double x2 = x * 8; double z2 = z * 8; m_ControlPoints = new Vector3D[4]; m_ControlPoints[0] = new Vector3D(x2, 0, z2 + 7); m_ControlPoints[1] = new Vector3D(x2 - 7, 0, z2); m_ControlPoints[2] = new Vector3D(x2, 0, z2 - 7); m_ControlPoints[3] = new Vector3D(x2 + 7, 0, z2); m_iControlPointsIndex = 0; break; case CLASS_ENGINEER: case CLASS_NONE: default: break; } }
/** * Este metodo inserta en una lista los enemigos a la vista y asigna a m_AimedAgent aquel q está * tiene menos vida, en el caso que tenga amigos a la vista, calcula la diferencia entre el ángulo * del m_AimedAgent y el amigo si es <=1, no dispara * * @return En el caso que hayan enemigos a la vista devuelve true y sino false. */ protected boolean GetAgentToAim_EnemigoMenosVida() { m_AimedAgent = null; // si no tengo ningún agente en el campo de visión devuelvo false if (m_FOVObjects.isEmpty()) { return false; } ArrayList<CSight> enemigos = new ArrayList<CSight>(); ArrayList<CSight> amigos = new ArrayList<CSight>(); boolean bfuegoAmigo = false; @SuppressWarnings("unchecked") Iterator<?> it = m_FOVObjects.iterator(); int iMenorVida = Integer.MAX_VALUE; int iVida = 0; CSight enemigoMenorVida = null; double distanciaAmigo = 0f; double distanciaEnemigo = 0f; while (it.hasNext()) { CSight s = (CSight) it.next(); if (s.getType() >= CPack.PACK_NONE) { continue; } int eTeam = s.getTeam(); if (m_eTeam != eTeam) // si se trata de un enemigo, se añade a la lista de enemigos. { enemigos.add(s); } else // si es amigo { amigos.add(s); } } if (!enemigos.isEmpty()) { for (int i = 0; i <= enemigos.size() - 1; i++) { iVida = enemigos.get(i).getHealth(); if (iVida < iMenorVida) { enemigoMenorVida = enemigos.get(i); iMenorVida = iVida; } } if (!amigos.isEmpty()) { for (int j = 0; j <= amigos.size() - 1; j++) { if (Math.abs(amigos.get(j).getAngle() - enemigoMenorVida.getAngle()) <= 1) // si estan en el mismo ángulo de tiro o con un grado de diferencia // No se dispara por peligro de fuego amigo { distanciaAmigo = this.distanciaManhattan(this.m_Movement.getPosition(), amigos.get(j)); distanciaEnemigo = this.distanciaManhattan(this.m_Movement.getPosition(), enemigoMenorVida); if (distanciaAmigo <= distanciaEnemigo) { bfuegoAmigo = true; } } } if (!bfuegoAmigo) // si no hay ningún amigo en mismo o +1 ángulo se dispara { m_AimedAgent = enemigoMenorVida; } } else // si no tengo amigos en el campo de visión se dispara. { m_AimedAgent = enemigoMenorVida; } } if (m_AimedAgent != null) { return true; } else { return false; } }
/** * Este metodo inserta en una lista los enemigos a la vista y asigna a m_AimedAgent aquel q está * más cercano,en el caso que tenga amigos a la vista, calcula la diferencia entre el ángulo del * m_AimedAgent y el amigo si es <=1, no dispara En el caso que hayan enemigos a la vista devuelve * true y sino false. * * @return */ protected boolean GetAgentToAim_EnemigoMasCercano() { m_AimedAgent = null; boolean bfuegoAmigo = false; // si no tengo ningún agente en el campo de visión devuelvo false if (m_FOVObjects.isEmpty()) { return false; } ArrayList<CSight> enemigos = new ArrayList<CSight>(); ArrayList<CSight> amigos = new ArrayList<CSight>(); @SuppressWarnings("unchecked") Iterator<?> it = m_FOVObjects.iterator(); double distanciaMenor = Double.MAX_VALUE; double distancia = 0f; CSight enemigoMascercano = null; while (it.hasNext()) { CSight s = (CSight) it.next(); if (s.getType() >= CPack.PACK_NONE) { continue; } int eTeam = s.getTeam(); if (m_eTeam != eTeam) // si se trata de un enemigo, se añade a la lista de enemigos. { enemigos.add(s); } else // si es amigo { amigos.add(s); } } if (!enemigos.isEmpty()) { for (int i = 0; i <= enemigos.size() - 1; i++) { distancia = this.distanciaManhattan(this.m_Movement.getPosition(), enemigos.get(i)); if (distancia < distanciaMenor) { enemigoMascercano = enemigos.get(i); distanciaMenor = distancia; } } if (!amigos.isEmpty()) { for (int j = 0; j <= amigos.size() - 1; j++) { if (Math.abs(amigos.get(j).getAngle() - enemigoMascercano.getAngle()) <= 1) // si estan en el mismo ángulo de tiro o con un grado de diferencia { if (this.distanciaManhattan(this.m_Movement.getPosition(), amigos.get(j)) <= distanciaMenor) // y ademas está a una distancia menor que el agente enmigo // No se dispara por peligro de fuego amigo bfuegoAmigo = true; } } if (!bfuegoAmigo) // si no hay ningún amigo en mismo o +1 ángulo y más cerca que el enemigo // se dispara { m_AimedAgent = enemigoMascercano; } } else // si no tengo amigos en el campo de visión se dispara. { m_AimedAgent = enemigoMascercano; } } if (m_AimedAgent != null) { return true; } else { return false; } }
/** * Calculates a new destiny position to walk. * * <p>This method is called before the agent creates a <tt> TASK_GOTO_POSITION</tt> task. It will * try (for 5 attempts) to generate a valid random point in a radius of 20 units. If it doesn't * generate a valid position in this cycle, it will try it in next cycle. Once a position is * calculated, agent updates its destination to the new position, and automatically calculates the * new direction. * * <p><em> It's very useful to overload this method. </em> * * @return <tt> TRUE</tt>: valid position generated / <tt> FALSE</tt> cannot generate a valid * position */ protected boolean GeneratePath() { bHeVuelto = false; m_iAStarPathIndex = 0; // inicilaizamos a 0 System.out.println( "La posicion inicial por getposition es " + m_Movement.getPosition().x + "y z es " + m_Movement.getPosition().z); Vector3D vNewDestination = new Vector3D(m_Movement.getPosition().x, 0.0, m_Movement.getPosition().z); ArrayList<Vector3D> lv3D = new ArrayList< Vector3D>(); // para ir metiendo los puntos que luego le pasaré en orden descendente a // m_AStarPath ArrayList<Nodo> lAbiertos = new ArrayList<Nodo>(); ArrayList<Nodo> lCerrados = new ArrayList<Nodo>(); ArrayList<Nodo> lvecinos = new ArrayList<Nodo>(); int xInit = (int) Math.floor(m_Movement.getPosition().x); xInit /= 8; int zInit = (int) Math.floor(m_Movement.getPosition().z); zInit /= 8; int xFinal = (int) Math.floor(m_Movement.getDestination().x); xFinal /= 8; int zFinal = (int) Math.floor(m_Movement.getDestination().z); zFinal /= 8; Nodo nodoInit = new Nodo(xInit, zInit, null); Nodo nodoFinal = new Nodo(xFinal, zFinal, null); Nodo nodoActual = null; lAbiertos.add(nodoInit); // añado el nodo inicial a la lista de abiertos boolean esNodoFinal = false; while (!esNodoFinal) // (!lAbiertos.isEmpty()){ { nodoActual = this.obtenerNodoMejorCoste( lAbiertos, nodoFinal); // obtener el nodo abierto de menor coste for (int i = 0; i < lAbiertos.size(); i++) { if (nodoActual.comparaEsNodo(lAbiertos.get(i))) { lAbiertos.remove(i); } } // System.out.println("2 Labiertos tiene"+lAbiertos.size()); // lAbiertos.remove(nodoActual); lCerrados.add(nodoActual); if (nodoActual.comparaEsNodo(nodoFinal)) { esNodoFinal = true; break; } lvecinos.clear(); lvecinos = this.calcularVecinos(lvecinos, nodoActual); lAbiertos = this.actualizarAbiertos(lAbiertos, lCerrados, lvecinos, nodoFinal); // System.out.println("Ha entrado en el bucle"); // System.out.println("Nodo Actual x:"+nodoActual.getPosX()+" y posicion z: // "+nodoActual.getPosZ()); } System.out.println("Ha salido"); boolean esInicial = false; for (int h = 0; h < lCerrados.size(); h++) { if (nodoFinal.comparaEsNodo(lCerrados.get(h))) { nodoFinal = lCerrados.get(h); } } Nodo nCurrent = nodoFinal; Nodo nPadre = null; while (!esInicial) // meto las posiciones de los nodos en un array de Vector3D { if (nCurrent.getPadre() == null) esInicial = true; lv3D.add(new Vector3D(nCurrent.getPosX() * 8, 0, nCurrent.getPosZ() * 8)); nCurrent = nCurrent.getPadre(); } Vector3D[] v3D = new Vector3D[lv3D.size()]; Vector3D[] v3DReturn = new Vector3D[1000]; for (int j = lv3D.size() - 1; j >= 0; j--) { // for(int h=0;h<lv3D.size();h++) // { v3D[(lv3D.size() - 1) - j] = new Vector3D(lv3D.get(j).x, 0.0, lv3D.get(j).z); // v3DReturn[j]=new Vector3D(lv3D.get(j).x,0.0,lv3D.get(j).z); // } } // System.out.println(m_Movement.getPosition().x); // System.out.println(m_Movement.getPosition().z); double xInicial = lv3D.get(0).x; double zInicial = lv3D.get(0).z; double xINI = v3D[0].x; double zINI = v3D[0].z; // this.setvVolverPath(v3DReturn);//Me guardo el vector para volver m_AStarPath = v3D; if (CheckStaticPosition(m_AStarPath[0].x, m_AStarPath[0].z) == true) { String posInit = " ( " + m_AStarPath[0].x + " , 0.0 , " + m_AStarPath[0].z + " ) "; AddTask(CTask.TASK_WALKING_PATH, getAID(), posInit, 10000); m_Movement.setDestination(vNewDestination); System.out.println( "la posicion inicial es " + vNewDestination.x + " y la z " + vNewDestination.z); System.out.println( "El destino actual es " + m_Movement.getDestination().x + " y la z " + m_Movement.getDestination().z); return true; } return false; }