mirror of
https://github.com/guilhermewerner/site-pi
synced 2025-06-17 06:14:19 +00:00
Initial commit
This commit is contained in:
279
SitePi/wwwroot/uploads/ALMA.java
Normal file
279
SitePi/wwwroot/uploads/ALMA.java
Normal file
@ -0,0 +1,279 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
/*
|
||||
* AffectEngine.java
|
||||
*
|
||||
* Copyright (c) 2005, 2006, 2007, 2008, Patrick Gebhard, DFKI GmbH
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* - Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* - Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
*
|
||||
* - Neither the name of the DFKI GmbH nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
import de.affect.emotion.Emotion;
|
||||
import de.affect.emotion.EmotionType;
|
||||
import de.affect.manage.AffectManager;
|
||||
import de.affect.manage.event.AffectUpdateEvent;
|
||||
import de.affect.manage.event.AffectUpdateListener;
|
||||
import de.affect.mood.Mood;
|
||||
import de.affect.xml.AffectOutputDocument;
|
||||
|
||||
import de.affect.xml.AffectInputDocument.AffectInput;
|
||||
import de.affect.xml.AffectInputDocument.AffectInput.Character;
|
||||
import de.affect.xml.AffectInputDocument.AffectInput.BasicEEC;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
/**
|
||||
* Provides the basic interface between Pogamut and ALMA.
|
||||
*
|
||||
* This code is based on the AffectEngine.java class provided with ALMA as an example
|
||||
* implementation.
|
||||
*
|
||||
* @author Patrick Gebhard, Michal Bida
|
||||
*/
|
||||
public class ALMA implements AffectUpdateListener {
|
||||
|
||||
/** The agent this PogamutALMA instance is for. */
|
||||
public EmotionalBot myAgent;
|
||||
/** The ALMA Java implementation */
|
||||
public static AffectManager fAM = null;
|
||||
|
||||
/** ALMA affect computation definition file */
|
||||
private static String sALMACOMP = "./conf/AffectComputation.aml";
|
||||
|
||||
/** ALMA character definition file */
|
||||
private static String sALMADEF = "./conf/CharacterDefinition.aml";
|
||||
|
||||
/** Current level time in seconds (contains also milliseconds after dot) */
|
||||
public double currentTime;
|
||||
|
||||
/* ALMA mode:
|
||||
false - output on console
|
||||
true - graphical user interface CharacterBuilder
|
||||
NOTE: No runtime windows (defined in AffectComputation or
|
||||
AffectDefinition will be displayed!) */
|
||||
private static final boolean sGUIMode = false;
|
||||
/** Console logging */
|
||||
public static Logger log = Logger.getLogger(Logger.GLOBAL_LOGGER_NAME);
|
||||
|
||||
/**
|
||||
* The constructor that sets up ALMA engine.
|
||||
*
|
||||
* @param agent
|
||||
*/
|
||||
public ALMA(EmotionalBot agent) {
|
||||
// Starting the ALMA affect engine
|
||||
myAgent = agent;
|
||||
|
||||
try {
|
||||
|
||||
//fAM = new AffectManager(sALMACOMP, sALMADEF, sGUIMode);
|
||||
fAM = new AffectManager(ALMA.class.getClassLoader().getResourceAsStream(sALMACOMP), ALMA.class.getClassLoader().getResourceAsStream(sALMADEF), sGUIMode);
|
||||
//disable alma logging
|
||||
fAM.log.setLevel(Level.OFF);
|
||||
fAM.addAffectUpdateListener(this);
|
||||
|
||||
} catch (IOException io) {
|
||||
log.info("Error during ALMA initialisation");
|
||||
io.printStackTrace();
|
||||
System.exit(-1);
|
||||
} catch (Exception xmle) {
|
||||
log.info("Error in ALMA configuration");
|
||||
xmle.printStackTrace();
|
||||
System.exit(-1);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Listens to affect updates computed by ALMA. This implements the AffectUpdateListener.
|
||||
*
|
||||
* Called each time something in ALMA is changed. In ALMA the affects are changing
|
||||
* very often resulting in this method getting called very often as well.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
public synchronized void update(AffectUpdateEvent event) {
|
||||
AffectOutputDocument aod = event.getUpdate();
|
||||
//nothing for now, logging?
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns current mood for target agent.
|
||||
*
|
||||
* @param agentName
|
||||
* @return
|
||||
*/
|
||||
public Mood getCurrentMood(String agentName) {
|
||||
return fAM.getCharacterByName(agentName).getCurrentMood();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets all emotions for target agent, that are felt toward the elicitor provided.
|
||||
*
|
||||
* @param agentName
|
||||
* @param elicitor
|
||||
* @return
|
||||
*/
|
||||
public List<Emotion> getAllEmotionsForElicitor(String agentName, String elicitor) {
|
||||
|
||||
ArrayList<Emotion> emotionList = new ArrayList<Emotion>();
|
||||
Emotion tempEm = null;
|
||||
|
||||
for (int j = 0; j < EmotionType.values().length; j++) {
|
||||
|
||||
//we get emotions one by one from ALMA history
|
||||
tempEm = fAM.getCharacterByName(agentName).getEmotionHistory().getEmotionByElicitor(EmotionType.values()[j], elicitor);
|
||||
if (tempEm != null) {
|
||||
emotionList.add(tempEm);
|
||||
}
|
||||
}
|
||||
|
||||
return emotionList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets emotion for target agent name of input type and for input elicitor.
|
||||
*
|
||||
* @param agentName
|
||||
* @param elicitor
|
||||
* @param type
|
||||
* @return
|
||||
*/
|
||||
public Emotion getEmotionForElicitor(String agentName, String elicitor, EmotionType type) {
|
||||
return fAM.getCharacterByName(agentName).getEmotionHistory().getEmotionByElicitor(type, elicitor);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets dominant emotion for the input agent.
|
||||
*
|
||||
* @param agentName
|
||||
* @return
|
||||
*/
|
||||
public Emotion getDominantEmotion(String agentName){
|
||||
return fAM.getCharacterByName(agentName).getCurrentEmotions().getDominantEmotion();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the ALMA current emotions (in characters focus) for target agent.
|
||||
*
|
||||
* @param agentName
|
||||
* @return
|
||||
*/
|
||||
public List<Emotion> getCurrentEmotions(String agentName) {
|
||||
if (fAM.getCharacterByName(agentName) != null) {
|
||||
return fAM.getCharacterByName(agentName).getCurrentEmotions().getEmotions();
|
||||
} else {
|
||||
return new ArrayList<Emotion>();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an AffectInput document containing an BasicEEC Element and returns a AffectInput object
|
||||
*
|
||||
* @param actor
|
||||
* @param desirability
|
||||
* @param agency
|
||||
* @param praiseworthiness
|
||||
* @param appealingness
|
||||
* @param liking
|
||||
* @param likelihood
|
||||
* @param elicitor
|
||||
* @param realization
|
||||
* @return
|
||||
*/
|
||||
public AffectInput createAffectInputBasicEEC(String actor,
|
||||
double desirability, double praiseworthiness, double appealingness, double likelihood,
|
||||
double liking, double realization, String elicitor, String agency) {
|
||||
|
||||
AffectInput aiInput = AffectInput.Factory.newInstance();
|
||||
// Building the Character element
|
||||
Character perfCharacter = Character.Factory.newInstance();
|
||||
perfCharacter.setName(actor);
|
||||
|
||||
BasicEEC eec = BasicEEC.Factory.newInstance();
|
||||
|
||||
eec.setDesirability(desirability);
|
||||
eec.setPraiseworthiness(praiseworthiness);
|
||||
eec.setAppealingness(appealingness);
|
||||
eec.setLikelihood(likelihood);
|
||||
eec.setLiking(liking);
|
||||
eec.setRealization(realization);
|
||||
eec.setAgency((agency.toLowerCase() == "self") ? BasicEEC.Agency.SELF : BasicEEC.Agency.OTHER);
|
||||
eec.setElicitor(elicitor);
|
||||
|
||||
aiInput.setCharacter(perfCharacter);
|
||||
aiInput.setBasicEEC(eec);
|
||||
|
||||
return aiInput;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an AffectInput document containing an BasicEEC Element and returns a AffectInput object
|
||||
* This type eec element is constructed elsewhere
|
||||
* @param actor
|
||||
* @param eec
|
||||
* @return
|
||||
*/
|
||||
public AffectInput createAffectInput(String actor, BasicEEC eec) {
|
||||
|
||||
AffectInput aiInput = AffectInput.Factory.newInstance();
|
||||
// Building the Character element
|
||||
Character perfCharacter = Character.Factory.newInstance();
|
||||
perfCharacter.setName(actor);
|
||||
|
||||
aiInput.setCharacter(perfCharacter);
|
||||
aiInput.setBasicEEC(eec);
|
||||
|
||||
return aiInput;
|
||||
}
|
||||
|
||||
/**
|
||||
* The <code>processAffectInput</code> passes instance of AffectInput to AffectManager
|
||||
* event string is here just for logging
|
||||
* @param ai
|
||||
* @param event
|
||||
*/
|
||||
public void processAffectInput(AffectInput ai, String event) {
|
||||
|
||||
myAgent.getLog().warning("Name: " + ai.getCharacter().getName() + " Event: " + event + " ${symbol_escape}n" + myAgent.currentTime +
|
||||
" Vars: D: " + ai.getBasicEEC().getDesirability() + "; P: " + ai.getBasicEEC().getPraiseworthiness() +
|
||||
"; A: " + ai.getBasicEEC().getAppealingness() + "; Lh: " + ai.getBasicEEC().getLikelihood() +
|
||||
"; Li: " + ai.getBasicEEC().getLiking() + "; R: " + ai.getBasicEEC().getRealization() +
|
||||
"; Ag: " + ai.getBasicEEC().getAgency() + "; El.: " + ai.getBasicEEC().getElicitor());
|
||||
|
||||
fAM.processSignal(ai);
|
||||
}
|
||||
}
|
||||
|
||||
|
534
SitePi/wwwroot/uploads/HideAndSeekBot.java
Normal file
534
SitePi/wwwroot/uploads/HideAndSeekBot.java
Normal file
@ -0,0 +1,534 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.IPathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.PathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.utils.guice.AgentScoped;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.utils.TabooSet;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.UT2004PathAutoFixer;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004Bot;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004BotModuleController;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Initialize;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotKilled;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ConfigChange;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ControlMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.InitedMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.NavPoint;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Player;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Self;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.bot.UT2004BotHSController;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.HSBotState;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.HSScoreChangeReason;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSAssignSeeker;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSBotStateChanged;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSPlayerScoreChanged;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRoundEnd;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRoundStart;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRoundState;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRunnerCaptured;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRunnerFouled;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRunnerSafe;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRunnerSpotted;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.protocol.messages.HSRunnerSurvived;
|
||||
import cz.cuni.amis.pogamut.ut2004.hideandseek.server.UT2004HSServer;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UT2004BotRunner;
|
||||
import cz.cuni.amis.utils.IFilter;
|
||||
import cz.cuni.amis.utils.collections.MyCollections;
|
||||
import cz.cuni.amis.utils.exception.PogamutException;
|
||||
import cz.cuni.amis.utils.flag.FlagListener;
|
||||
|
||||
/**
|
||||
* Example of the bot playing HIDE-AND-SEEK-GAME according to {@link ControlMessage}s from {@link UT2004HSServer}.
|
||||
*
|
||||
* @author Jakub Gemrot aka Jimmy
|
||||
*/
|
||||
@AgentScoped
|
||||
public class HideAndSeekBot extends UT2004BotHSController<UT2004Bot> {
|
||||
|
||||
private static String[] names = new String[]{"Peter", "James", "Johnny", "Craig", "Jimmy", "Steve", "Ronnie", "Bobby"};
|
||||
|
||||
static {
|
||||
List<String> n = MyCollections.toList(names);
|
||||
Collections.shuffle(n);
|
||||
names = n.toArray(new String[n.size()]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Just for the numbering of bots.
|
||||
*/
|
||||
private static int number = 0;
|
||||
|
||||
/**
|
||||
* Taboo set is working as "black-list", that is you might add some
|
||||
* NavPoints to it for a certain time, marking them as "unavailable".
|
||||
*/
|
||||
protected TabooSet<NavPoint> tabooNavPoints;
|
||||
|
||||
/**
|
||||
* Path auto fixer watches for navigation failures and if some navigation
|
||||
* link is found to be unwalkable, it removes it from underlying navigation
|
||||
* graph.
|
||||
*
|
||||
* Note that UT2004 navigation graphs are some times VERY stupid or contains
|
||||
* VERY HARD TO FOLLOW links...
|
||||
*/
|
||||
protected UT2004PathAutoFixer autoFixer;
|
||||
|
||||
/**
|
||||
* Here we can modify initializing command for our bot.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Initialize getInitializeCommand() {
|
||||
return new Initialize().setName(names[(++number) % names.length]);
|
||||
}
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public void botInitialized(GameInfo gameInfo, ConfigChange config, InitedMessage init) {
|
||||
// initialize taboo set where we store temporarily unavailable navpoints
|
||||
tabooNavPoints = new TabooSet<NavPoint>(bot);
|
||||
|
||||
// auto-removes wrong navigation links between navpoints
|
||||
autoFixer = new UT2004PathAutoFixer(bot, navigation.getPathExecutor(), fwMap, aStar, navBuilder);
|
||||
|
||||
// IMPORTANT
|
||||
// adds a listener to the path executor for its state changes, it will allow you to
|
||||
// react on stuff like "PATH TARGET REACHED" or "BOT STUCK"
|
||||
navigation.getPathExecutor().getState().addStrongListener(new FlagListener<IPathExecutorState>() {
|
||||
|
||||
@Override
|
||||
public void flagChanged(IPathExecutorState changedValue) {
|
||||
pathExecutorStateChange(changedValue.getState());
|
||||
}
|
||||
});
|
||||
|
||||
navigation.getLog().setLevel(Level.INFO);
|
||||
|
||||
// ((SocketConnection)bot.getEventBus().getComponent(SocketConnection.COMPONENT_ID)).setLogMessages(true);
|
||||
// bot.getLogger().getCategory(SocketConnection.COMPONENT_ID.getToken()).setLevel(Level.ALL);
|
||||
// bot.getLogger().getCategory(YylexParser.COMPONENT_ID.getToken()).setLevel(Level.ALL);
|
||||
}
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@Override
|
||||
public void botFirstSpawn(GameInfo gameInfo, ConfigChange config, InitedMessage init, Self self) {
|
||||
// change to ALL to receive logs from the navigation so you can get a grasp on how it is working
|
||||
navigation.getPathExecutor().getLog().setLevel(Level.WARNING);
|
||||
}
|
||||
|
||||
// --------------------
|
||||
// ====================
|
||||
// HIDE AND SEEK EVENTS
|
||||
// ====================
|
||||
// --------------------
|
||||
|
||||
/**
|
||||
* Some RUNNER has just survived the round.
|
||||
* <p><p>
|
||||
* This event is triggered at the end of the round for every RUNNER that has not been FOULED, CAPTURED and did not make it to SAFE area.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
protected void hsRunnerSurvived(HSRunnerSurvived event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Some RUNNER has just been spotted by the SEEKER.
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
protected void hsRunnerSpotted(HSRunnerSpotted event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Some RUNNER has just made it to the safe-area.
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
protected void hsRunnerSafe(HSRunnerSafe event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Some RUNNER has just been fouled-out because it stepped into the restricted-area while it was activated.
|
||||
* @param event
|
||||
* @param me whether this event speaks about your bot
|
||||
*/
|
||||
@Override
|
||||
protected void hsRunnerFouled(HSRunnerFouled event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Some RUNNER has just been captured by the SEEKER, i.e., seeker has spotted the runner and made it to the safe-area before
|
||||
* the runner.
|
||||
*
|
||||
* @param event
|
||||
* @param me whether this event speaks about your bot
|
||||
*/
|
||||
@Override
|
||||
protected void hsRunnerCaptured(HSRunnerCaptured event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Round state update has been received.
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
protected void hsRoundState(HSRoundState event) {
|
||||
}
|
||||
|
||||
/**
|
||||
* New round has just started, you may use this event to initialize your data-structures.
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
protected void hsRoundStart(HSRoundStart event) {
|
||||
hideNavPoint = null;
|
||||
targetNavPoint = null;
|
||||
goingToFoul = random.nextInt(6) == 5; // 1/6 probability that the RUNNER will perform FOUL BEHAVIOR, will remain in restricted area instead of hiding
|
||||
tabooNavPoints.clear();
|
||||
navigation.stopNavigation(); // prevent commands from previous round to be still effective
|
||||
}
|
||||
|
||||
/**
|
||||
* Round has just ended, you may use this event to cleanup your data-structures.
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
protected void hsRoundEnd(HSRoundEnd event) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Some player (runner/seeker) score has just changed, you may examine the reason within {@link HSPlayerScoreChanged${symbol_pound}getScoreChangeReason()}, see
|
||||
* {@link HSScoreChangeReason}.
|
||||
*
|
||||
* @param event
|
||||
* @param me whether this event speaks about your bot
|
||||
*/
|
||||
@Override
|
||||
protected void hsPlayerScoreChanged(HSPlayerScoreChanged event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Some bot {@link HSBotState} has been updated.
|
||||
* @param event
|
||||
* @param me whether this event speaks about your bot
|
||||
*/
|
||||
protected void hsBotStateChanged(HSBotStateChanged event, boolean me) {
|
||||
}
|
||||
|
||||
/**
|
||||
* SEEKER role has been just assigned to some bot.
|
||||
* @param event
|
||||
* @param me whether this event speaks about your bot
|
||||
*/
|
||||
@Override
|
||||
protected void hsAssignSeeker(HSAssignSeeker event, boolean me) {
|
||||
}
|
||||
|
||||
// -----
|
||||
// =====
|
||||
// LOGIC
|
||||
// =====
|
||||
// -----
|
||||
|
||||
/**
|
||||
* This method is called only once right before actual logic() method is
|
||||
* called for the first time.
|
||||
*/
|
||||
@Override
|
||||
public void beforeFirstLogic() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Main method that controls the bot - makes decisions what to do next. It
|
||||
* is called iteratively by Pogamut engine every time a synchronous batch
|
||||
* from the environment is received. This is usually 4 times per second - it
|
||||
* is affected by visionTime variable, that can be adjusted in GameBots ini
|
||||
* file in UT2004/System folder.
|
||||
*/
|
||||
@Override
|
||||
public void logic() {
|
||||
// mark that another logic iteration has began
|
||||
log.info("====== LOGIC ITERATION ======");
|
||||
|
||||
// UNCOMMENT TO GET DETAIL INFO DURING RUN-TIME
|
||||
// logState();
|
||||
|
||||
if (!hide.isRoundRunning()) return;
|
||||
|
||||
if (!hide.isMeAlive()) return;
|
||||
|
||||
switch(hide.getMyState()) {
|
||||
case RUNNER:
|
||||
logicRunner();
|
||||
break;
|
||||
case RUNNER_SPOTTED:
|
||||
logicRunnerSpotted();
|
||||
break;
|
||||
case SEEKER:
|
||||
logicSeeker();
|
||||
break;
|
||||
default:
|
||||
// SHOULD NOT REACH HERE, BUT LET'S PLAY SAFE...
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
private void logState() {
|
||||
log.info("------ STATE ------");
|
||||
log.info("Game state: " + hide.getGameState());
|
||||
log.info("Game running: " + hide.isGameRunning());
|
||||
if (!hide.isGameRunning()) return;
|
||||
log.info("Round running: " + hide.isRoundRunning());
|
||||
if (!hide.isRoundRunning()) return;
|
||||
log.info("Me: " + hide.getMyState());
|
||||
log.info("Me spawned? " + hide.isMeAlive());
|
||||
log.info("Hiding time left: " + hide.getRemainingHidingTime());
|
||||
log.info("Restricted area time left: " + hide.getRemainingRestrictedAreaTime());
|
||||
log.info("Round time left: " + hide.getRemainingRoundTime());
|
||||
log.info("Distance to safe-area: " + hide.getMySafeAreaDistance());
|
||||
log.info("Distance to restricted-area: " + hide.getMyRestrictedAreaDistance());
|
||||
}
|
||||
|
||||
// ------------
|
||||
// ============
|
||||
// LOGIC RUNNER
|
||||
// ============
|
||||
// ------------
|
||||
|
||||
NavPoint hideNavPoint;
|
||||
|
||||
Boolean goingToFoul = null;
|
||||
|
||||
private void logicRunner() {
|
||||
log.info("------ RUNNER ------");
|
||||
if (hide.isHidingTime()) {
|
||||
if (goingToFoul) {
|
||||
log.info("GOING TO FOUL! Standing-stil...");
|
||||
return;
|
||||
}
|
||||
log.info("HIDING!");
|
||||
if (hideNavPoint == null) {
|
||||
hideNavPoint = chooseHideNavPoint();
|
||||
if (hideNavPoint == null) {
|
||||
log.warning("THERE IS NO SUITABLE HIDE-POINT TO RUN TO!");
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (info.isAtLocation(hideNavPoint)) {
|
||||
if (navigation.isNavigating()) {
|
||||
navigation.stopNavigation();
|
||||
}
|
||||
log.info("HIDDEN!");
|
||||
move.turnHorizontal(30);
|
||||
return;
|
||||
}
|
||||
navigation.navigate(hideNavPoint);
|
||||
return;
|
||||
}
|
||||
|
||||
if (hide.isRestrictedAreaActivated()) {
|
||||
log.info("RESTRICTED AREA ACTIVE, standing still!");
|
||||
return;
|
||||
}
|
||||
|
||||
runToSafePoint();
|
||||
}
|
||||
|
||||
private NavPoint chooseHideNavPoint() {
|
||||
if (visibility.isInitialized()) {
|
||||
// WE HAVE VISIBILITY INFORMATION!
|
||||
// => lets get smarty!
|
||||
return
|
||||
MyCollections.getRandomFiltered(
|
||||
visibility.getCoverNavPointsFrom(hide.getSafeArea()),
|
||||
new IFilter<NavPoint>() {
|
||||
@Override
|
||||
public boolean isAccepted(NavPoint object) {
|
||||
return !hide.isInRestrictedArea(object, 50);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
// NO VISIBILITY INFORMATION PROVIDED, CHOOSE RANDOM SUITABLE
|
||||
return
|
||||
MyCollections.getRandomFiltered(
|
||||
navPoints.getNavPoints().values(),
|
||||
new IFilter<NavPoint>() {
|
||||
@Override
|
||||
public boolean isAccepted(NavPoint object) {
|
||||
return !hide.isInRestrictedArea(object, 50);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
// --------------------
|
||||
// ====================
|
||||
// LOGIC RUNNER SPOTTED
|
||||
// ====================
|
||||
// --------------------
|
||||
|
||||
private void logicRunnerSpotted() {
|
||||
runToSafePoint();
|
||||
}
|
||||
|
||||
private void runToSafePoint() {
|
||||
log.info("RUNNING TO SAFE POINT");
|
||||
navigation.navigate(hide.getSafeArea());
|
||||
}
|
||||
|
||||
// ------------
|
||||
// ============
|
||||
// LOGIC SEEKER
|
||||
// ============
|
||||
// ------------
|
||||
|
||||
private void logicSeeker() {
|
||||
log.info("------ SEEKER ------");
|
||||
if (hide.canCaptureRunner()) {
|
||||
log.info("CAN CAPTURE RUNNER!");
|
||||
runToSafePoint();
|
||||
} else {
|
||||
if (players.canSeePlayers()) {
|
||||
targetNavPoint = null;
|
||||
handlePlayerNavigation(players.getNearestVisiblePlayer());
|
||||
} else {
|
||||
handleNavPointNavigation();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private NavPoint targetNavPoint;
|
||||
|
||||
private void handleNavPointNavigation() {
|
||||
if (navigation.isNavigatingToNavPoint()) {
|
||||
// IS TARGET CLOSE & NEXT TARGET NOT SPECIFIED?
|
||||
while (navigation.getContinueTo() == null && navigation.getRemainingDistance() < 400) {
|
||||
// YES, THERE IS NO "next-target" SET AND WE'RE ABOUT TO REACH OUR TARGET!
|
||||
navigation.setContinueTo(getRandomNavPoint());
|
||||
// note that it is WHILE because navigation may immediately eat up "next target" and next target may be actually still too close!
|
||||
}
|
||||
|
||||
// WE'RE NAVIGATING TO SOME NAVPOINT
|
||||
return;
|
||||
}
|
||||
|
||||
// NAVIGATION HAS STOPPED ...
|
||||
// => we need to choose another navpoint to navigate to
|
||||
// => possibly follow some players ...
|
||||
|
||||
targetNavPoint = getRandomNavPoint();
|
||||
if (targetNavPoint == null) {
|
||||
log.severe("COULD NOT CHOOSE ANY NAVIGATION POINT TO RUN TO!!!");
|
||||
if (world.getAll(NavPoint.class).size() == 0) {
|
||||
log.severe("world.getAll(NavPoint.class).size() == 0, there are no navigation ponits to choose from! Is exporting of nav points enabled in GameBots2004.ini inside UT2004?");
|
||||
}
|
||||
config.setName("NavigationBot [CRASHED]");
|
||||
return;
|
||||
}
|
||||
|
||||
navigation.navigate(targetNavPoint);
|
||||
}
|
||||
|
||||
private void handlePlayerNavigation(Player player) {
|
||||
if (navigation.isNavigating() && navigation.getCurrentTargetPlayer() == player) {
|
||||
// WE'RE NAVIGATING TO SOME PLAYER
|
||||
return;
|
||||
}
|
||||
|
||||
// START THE NAVIGATION
|
||||
navigation.navigate(player);
|
||||
}
|
||||
|
||||
/**
|
||||
* Called each time our bot die. Good for reseting all bot state dependent
|
||||
* variables.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
public void botKilled(BotKilled event) {
|
||||
navigation.stopNavigation();
|
||||
}
|
||||
|
||||
/**
|
||||
* Path executor has changed its state (note that {@link UT2004BotModuleController${symbol_pound}getPathExecutor()}
|
||||
* is internally used by
|
||||
* {@link UT2004BotModuleController${symbol_pound}getNavigation()} as well!).
|
||||
*
|
||||
* @param state
|
||||
*/
|
||||
protected void pathExecutorStateChange(PathExecutorState state) {
|
||||
switch (state) {
|
||||
case PATH_COMPUTATION_FAILED:
|
||||
// if path computation fails to whatever reason, just try another navpoint
|
||||
// taboo bad navpoint for 10 seconds
|
||||
tabooNavPoints.add(targetNavPoint, 10);
|
||||
break;
|
||||
|
||||
case TARGET_REACHED:
|
||||
// taboo reached navpoint for 10 seconds
|
||||
tabooNavPoints.add(targetNavPoint, 10);
|
||||
break;
|
||||
|
||||
case STUCK:
|
||||
// the bot has stuck! ... target nav point is unavailable currently
|
||||
tabooNavPoints.add(targetNavPoint, 30);
|
||||
break;
|
||||
|
||||
case STOPPED:
|
||||
// path execution has stopped
|
||||
targetNavPoint = null;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Randomly picks some navigation point to head to.
|
||||
*
|
||||
* @return randomly choosed navpoint
|
||||
*/
|
||||
protected NavPoint getRandomNavPoint() {
|
||||
log.info("Picking new target navpoint.");
|
||||
|
||||
// choose one feasible navpoint (== not belonging to tabooNavPoints) randomly
|
||||
NavPoint chosen = MyCollections.getRandomFiltered(navPoints.getNavPoints().values(), tabooNavPoints);
|
||||
|
||||
if (chosen != null) {
|
||||
return chosen;
|
||||
}
|
||||
|
||||
log.warning("All navpoints are tabooized at this moment, choosing navpoint randomly!");
|
||||
|
||||
// ok, all navpoints have been visited probably, try to pick one at random
|
||||
return MyCollections.getRandom(navPoints.getNavPoints().values());
|
||||
}
|
||||
|
||||
public static void main(String args[]) throws PogamutException {
|
||||
// Starts 1 bot
|
||||
// If you want to execute the whole Hide&Seek game/match, execute {@link HideAndSeekGame}.
|
||||
new UT2004BotRunner(HideAndSeekBot.class, "HSBot").setMain(true).setLogLevel(Level.WARNING).startAgents(1);
|
||||
}
|
||||
}
|
282
SitePi/wwwroot/uploads/HideBot.java
Normal file
282
SitePi/wwwroot/uploads/HideBot.java
Normal file
@ -0,0 +1,282 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.IPathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.PathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.utils.guice.AgentScoped;
|
||||
import cz.cuni.amis.pogamut.base.utils.math.DistanceUtils;
|
||||
import cz.cuni.amis.pogamut.base3d.worldview.object.ILocated;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.sensor.visibility.Visibility;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.sensor.visibility.VisibilityCreator;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.utils.TabooSet;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.UT2004PathAutoFixer;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004BotModuleController;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Initialize;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotKilled;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ConfigChange;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.InitedMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.NavPoint;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Player;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UT2004BotRunner;
|
||||
import cz.cuni.amis.utils.Cooldown;
|
||||
import cz.cuni.amis.utils.Heatup;
|
||||
import cz.cuni.amis.utils.collections.MyCollections;
|
||||
import cz.cuni.amis.utils.exception.PogamutException;
|
||||
import cz.cuni.amis.utils.flag.FlagListener;
|
||||
|
||||
/**
|
||||
* Example of Pogamut Bot that is utilizing {@link Visibility} module.
|
||||
*
|
||||
* Must be run on DM-1on1-Albatross. If you want to use different map
|
||||
* read javadoc for {@link Visibility} and {@link VisibilityCreator}.
|
||||
*
|
||||
* @author Jakub Gemrot aka Jimmy
|
||||
*/
|
||||
@AgentScoped
|
||||
public class HideBot extends UT2004BotModuleController {
|
||||
|
||||
/**
|
||||
* Taboo set is working as "black-list", that is you might add some
|
||||
* NavPoints to it for a certain time, marking them as "unavailable".
|
||||
*/
|
||||
protected TabooSet<NavPoint> tabooNavPoints;
|
||||
|
||||
/**
|
||||
* Used for autofixing navpoints.
|
||||
*/
|
||||
protected UT2004PathAutoFixer autoFixer;
|
||||
|
||||
/**
|
||||
* Here we can modify initializing command for our bot.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Initialize getInitializeCommand() {
|
||||
return new Initialize().setName("HideBot");
|
||||
}
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public void botInitialized(GameInfo gameInfo, ConfigChange config, InitedMessage init) {
|
||||
// initialize taboo set where we store temporarily unavailable navpoints
|
||||
tabooNavPoints = new TabooSet<NavPoint>(bot);
|
||||
|
||||
// auto-removes wrong navigation links between navpoints
|
||||
autoFixer = new UT2004PathAutoFixer(bot, navigation.getPathExecutor(), fwMap, aStar, navBuilder);
|
||||
|
||||
// IMPORTANT
|
||||
// adds a listener to the path executor for its state changes, it will allow you to
|
||||
// react on stuff like "PATH TARGET REACHED" or "BOT STUCK"
|
||||
navigation.getPathExecutor().getState().addStrongListener(new FlagListener<IPathExecutorState>() {
|
||||
|
||||
@Override
|
||||
public void flagChanged(IPathExecutorState changedValue) {
|
||||
pathExecutorStateChange(changedValue.getState());
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
Player hidingFrom;
|
||||
|
||||
Heatup hiding = new Heatup(10000);
|
||||
|
||||
Cooldown turning = new Cooldown(1200);
|
||||
|
||||
NavPoint targetNavPoint;
|
||||
|
||||
Cooldown changeNavPoint = new Cooldown(2000);
|
||||
|
||||
@Override
|
||||
public void logic() {
|
||||
|
||||
if (!visibility.isInitialized()) {
|
||||
log.warning("Could not use VISIBILITY module :-(");
|
||||
return;
|
||||
}
|
||||
|
||||
Player visible = players.getNearestVisiblePlayer();
|
||||
|
||||
if (hidingFrom != null) {
|
||||
|
||||
if (visible != hidingFrom) {
|
||||
if (!hidingFrom.isVisible()) {
|
||||
// SWITCH ATTENTION
|
||||
startRunningAwayFrom(visible);
|
||||
return;
|
||||
}
|
||||
|
||||
if (info.getLocation().getDistance(visible.getLocation()) < info.getLocation().getDistance(hidingFrom.getLocation())) {
|
||||
// SWITCH ATTENTION
|
||||
startRunningAwayFrom(hidingFrom);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
continueRunningAwayFrom();
|
||||
return;
|
||||
}
|
||||
|
||||
if (visible != null) {
|
||||
startRunningAwayFrom(visible);
|
||||
return;
|
||||
}
|
||||
|
||||
if (navigation.isNavigating()) {
|
||||
navigation.stopNavigation();
|
||||
navigation.setFocus(null);
|
||||
}
|
||||
|
||||
if (turning.tryUse()) {
|
||||
move.turnHorizontal(110);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void startRunningAwayFrom(Player enemy) {
|
||||
this.hidingFrom = enemy;
|
||||
NavPoint cover = getCoverNavPoint(enemy);
|
||||
|
||||
if (cover == null) {
|
||||
log.warning("No suitable navpoint, standing still... :-(");
|
||||
return;
|
||||
}
|
||||
|
||||
navigation.setFocus(enemy);
|
||||
runTo(cover);
|
||||
}
|
||||
|
||||
private NavPoint getCoverNavPoint(ILocated enemy) {
|
||||
Set<NavPoint> navPoints = visibility.getCoverNavPointsFrom(enemy);
|
||||
|
||||
NavPoint cover = DistanceUtils.getNearestFiltered(navPoints, info.getLocation(), tabooNavPoints);
|
||||
|
||||
if (cover != null) return cover;
|
||||
|
||||
log.warning("Could not use any navpoint as cover... trying random one.");
|
||||
return getRandomNavPoint();
|
||||
}
|
||||
|
||||
private void continueRunningAwayFrom() {
|
||||
if (hidingFrom == null) {
|
||||
log.warning("hidingFrom == null ???");
|
||||
return;
|
||||
}
|
||||
|
||||
if (navigation.isNavigating()) {
|
||||
NavPoint suitableNavPoint = getCoverNavPoint(hidingFrom);
|
||||
if (targetNavPoint != suitableNavPoint) {
|
||||
if (changeNavPoint.tryUse()) {
|
||||
runTo(suitableNavPoint);
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// NOT NAVIGATING!
|
||||
if (targetNavPoint != null) {
|
||||
tabooNavPoints.add(targetNavPoint, 30);
|
||||
}
|
||||
|
||||
if (hidingFrom.isVisible()) {
|
||||
startRunningAwayFrom(hidingFrom);
|
||||
return;
|
||||
}
|
||||
|
||||
// NOT NAVIGATING! Player not visible...
|
||||
this.hidingFrom = null;
|
||||
}
|
||||
|
||||
|
||||
private void runTo(NavPoint navPoint) {
|
||||
log.info("Running to: " + navPoint);
|
||||
targetNavPoint = navPoint;
|
||||
navigation.navigate(targetNavPoint);
|
||||
}
|
||||
|
||||
/**
|
||||
* Called each time our bot die. Good for reseting all bot state dependent variables.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
public void botKilled(BotKilled event) {
|
||||
navigation.stopNavigation();
|
||||
targetNavPoint = null;
|
||||
hidingFrom = null;
|
||||
hiding.clear();
|
||||
turning.clear();
|
||||
changeNavPoint.clear();
|
||||
}
|
||||
|
||||
/**
|
||||
* Path executor has changed its state (note that {@link UT2004BotModuleController${symbol_pound}getPathExecutor()}
|
||||
* is internally used by
|
||||
* {@link UT2004BotModuleController${symbol_pound}getNavigation()} as well!).
|
||||
*
|
||||
* @param state
|
||||
*/
|
||||
protected void pathExecutorStateChange(PathExecutorState state) {
|
||||
switch (state) {
|
||||
case PATH_COMPUTATION_FAILED:
|
||||
// if path computation fails to whatever reason, just try another navpoint
|
||||
// taboo bad navpoint for 3 minutes
|
||||
tabooNavPoints.add(targetNavPoint, 180);
|
||||
break;
|
||||
|
||||
case TARGET_REACHED:
|
||||
tabooNavPoints.add(targetNavPoint, 5);
|
||||
break;
|
||||
|
||||
case STUCK:
|
||||
// the bot has stuck! ... target nav point is unavailable currently
|
||||
tabooNavPoints.add(targetNavPoint, 60);
|
||||
break;
|
||||
|
||||
case STOPPED:
|
||||
// path execution has stopped
|
||||
targetNavPoint = null;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Randomly picks some navigation point to head to.
|
||||
*
|
||||
* @return randomly choosed navpoint
|
||||
*/
|
||||
protected NavPoint getRandomNavPoint() {
|
||||
log.info("Picking new target navpoint.");
|
||||
|
||||
// choose one feasible navpoint (== not belonging to tabooNavPoints) randomly
|
||||
NavPoint chosen = MyCollections.getRandomFiltered(getWorldView().getAll(NavPoint.class).values(), tabooNavPoints);
|
||||
|
||||
if (chosen != null) {
|
||||
return chosen;
|
||||
}
|
||||
|
||||
log.warning("All navpoints are tabooized at this moment, choosing navpoint randomly!");
|
||||
|
||||
// ok, all navpoints have been visited probably, try to pick one at random
|
||||
return MyCollections.getRandom(getWorldView().getAll(NavPoint.class).values());
|
||||
}
|
||||
|
||||
public static void main(String args[]) throws PogamutException {
|
||||
// wrapped logic for bots executions, suitable to run single bot in single JVM
|
||||
|
||||
// we're forcingly setting logging to aggressive level FINER so you can see (almost) all logs
|
||||
// that describes decision making behind movement of the bot as well as incoming environment events
|
||||
new UT2004BotRunner(HideBot.class, "HideBot").setMain(true).setLogLevel(Level.INFO).startAgent();
|
||||
}
|
||||
}
|
414
SitePi/wwwroot/uploads/HunterBot.java
Normal file
414
SitePi/wwwroot/uploads/HunterBot.java
Normal file
@ -0,0 +1,414 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import cz.cuni.amis.introspection.java.JProp;
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.IPathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.EventListener;
|
||||
import cz.cuni.amis.pogamut.base.utils.Pogamut;
|
||||
import cz.cuni.amis.pogamut.base.utils.guice.AgentScoped;
|
||||
import cz.cuni.amis.pogamut.base.utils.math.DistanceUtils;
|
||||
import cz.cuni.amis.pogamut.base3d.worldview.object.ILocated;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.utils.TabooSet;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.NavigationState;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.UT2004PathAutoFixer;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.stuckdetector.UT2004DistanceStuckDetector;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.stuckdetector.UT2004PositionStuckDetector;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.stuckdetector.UT2004TimeStuckDetector;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004Bot;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004BotModuleController;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.ItemType;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.UT2004ItemType;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Initialize;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Move;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Rotate;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Stop;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.StopShooting;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotDamaged;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotKilled;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Item;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.NavPoint;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Player;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerDamaged;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerKilled;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UT2004BotRunner;
|
||||
import cz.cuni.amis.utils.collections.MyCollections;
|
||||
import cz.cuni.amis.utils.exception.PogamutException;
|
||||
import cz.cuni.amis.utils.flag.FlagListener;
|
||||
|
||||
/**
|
||||
* Example of Simple Pogamut bot, that randomly walks around the map searching
|
||||
* for preys shooting at everything that is in its way.
|
||||
*
|
||||
* @author Rudolf Kadlec aka ik
|
||||
* @author Jimmy
|
||||
*/
|
||||
@AgentScoped
|
||||
public class HunterBot extends UT2004BotModuleController<UT2004Bot> {
|
||||
|
||||
/**
|
||||
* boolean switch to activate engage behavior
|
||||
*/
|
||||
@JProp
|
||||
public boolean shouldEngage = true;
|
||||
/**
|
||||
* boolean switch to activate pursue behavior
|
||||
*/
|
||||
@JProp
|
||||
public boolean shouldPursue = true;
|
||||
/**
|
||||
* boolean switch to activate rearm behavior
|
||||
*/
|
||||
@JProp
|
||||
public boolean shouldRearm = true;
|
||||
/**
|
||||
* boolean switch to activate collect health behavior
|
||||
*/
|
||||
@JProp
|
||||
public boolean shouldCollectHealth = true;
|
||||
/**
|
||||
* how low the health level should be to start collecting health items
|
||||
*/
|
||||
@JProp
|
||||
public int healthLevel = 75;
|
||||
/**
|
||||
* how many bot the hunter killed other bots (i.e., bot has fragged them /
|
||||
* got point for killing somebody)
|
||||
*/
|
||||
@JProp
|
||||
public int frags = 0;
|
||||
/**
|
||||
* how many times the hunter died
|
||||
*/
|
||||
@JProp
|
||||
public int deaths = 0;
|
||||
|
||||
/**
|
||||
* {@link PlayerKilled} listener that provides "frag" counting + is switches
|
||||
* the state of the hunter.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
@EventListener(eventClass = PlayerKilled.class)
|
||||
public void playerKilled(PlayerKilled event) {
|
||||
if (event.getKiller().equals(info.getId())) {
|
||||
++frags;
|
||||
}
|
||||
if (enemy == null) {
|
||||
return;
|
||||
}
|
||||
if (enemy.getId().equals(event.getId())) {
|
||||
enemy = null;
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Used internally to maintain the information about the bot we're currently
|
||||
* hunting, i.e., should be firing at.
|
||||
*/
|
||||
protected Player enemy = null;
|
||||
/**
|
||||
* Item we're running for.
|
||||
*/
|
||||
protected Item item = null;
|
||||
/**
|
||||
* Taboo list of items that are forbidden for some time.
|
||||
*/
|
||||
protected TabooSet<Item> tabooItems = null;
|
||||
|
||||
private UT2004PathAutoFixer autoFixer;
|
||||
|
||||
private static int instanceCount = 0;
|
||||
|
||||
/**
|
||||
* Bot's preparation - called before the bot is connected to GB2004 and
|
||||
* launched into UT2004.
|
||||
*/
|
||||
@Override
|
||||
public void prepareBot(UT2004Bot bot) {
|
||||
tabooItems = new TabooSet<Item>(bot);
|
||||
|
||||
autoFixer = new UT2004PathAutoFixer(bot, navigation.getPathExecutor(), fwMap, aStar, navBuilder); // auto-removes wrong navigation links between navpoints
|
||||
|
||||
// listeners
|
||||
navigation.getState().addListener(new FlagListener<NavigationState>() {
|
||||
|
||||
@Override
|
||||
public void flagChanged(NavigationState changedValue) {
|
||||
switch (changedValue) {
|
||||
case PATH_COMPUTATION_FAILED:
|
||||
case STUCK:
|
||||
if (item != null) {
|
||||
tabooItems.add(item, 10);
|
||||
}
|
||||
reset();
|
||||
break;
|
||||
|
||||
case TARGET_REACHED:
|
||||
reset();
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
// DEFINE WEAPON PREFERENCES
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.LIGHTNING_GUN, true);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.SHOCK_RIFLE, true);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.MINIGUN, false);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.FLAK_CANNON, true);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.ROCKET_LAUNCHER, true);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.LINK_GUN, true);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.ASSAULT_RIFLE, true);
|
||||
weaponPrefs.addGeneralPref(UT2004ItemType.BIO_RIFLE, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Here we can modify initializing command for our bot.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Initialize getInitializeCommand() {
|
||||
// just set the name of the bot and his skill level, 1 is the lowest, 7 is the highest
|
||||
// skill level affects how well will the bot aim
|
||||
return new Initialize().setName("Hunter-" + (++instanceCount)).setDesiredSkill(5);
|
||||
}
|
||||
|
||||
/**
|
||||
* Resets the state of the Hunter.
|
||||
*/
|
||||
protected void reset() {
|
||||
item = null;
|
||||
enemy = null;
|
||||
navigation.stopNavigation();
|
||||
itemsToRunAround = null;
|
||||
}
|
||||
|
||||
@EventListener(eventClass=PlayerDamaged.class)
|
||||
public void playerDamaged(PlayerDamaged event) {
|
||||
log.info("I have just hurt other bot for: " + event.getDamageType() + "[" + event.getDamage() + "]");
|
||||
}
|
||||
|
||||
@EventListener(eventClass=BotDamaged.class)
|
||||
public void botDamaged(BotDamaged event) {
|
||||
log.info("I have just been hurt by other bot for: " + event.getDamageType() + "[" + event.getDamage() + "]");
|
||||
}
|
||||
|
||||
/**
|
||||
* Main method that controls the bot - makes decisions what to do next. It
|
||||
* is called iteratively by Pogamut engine every time a synchronous batch
|
||||
* from the environment is received. This is usually 4 times per second - it
|
||||
* is affected by visionTime variable, that can be adjusted in GameBots ini
|
||||
* file in UT2004/System folder.
|
||||
*
|
||||
* @throws cz.cuni.amis.pogamut.base.exceptions.PogamutException
|
||||
*/
|
||||
@Override
|
||||
public void logic() {
|
||||
// 1) do you see enemy? -> go to PURSUE (start shooting / hunt the enemy)
|
||||
if (shouldEngage && players.canSeeEnemies() && weaponry.hasLoadedWeapon()) {
|
||||
stateEngage();
|
||||
return;
|
||||
}
|
||||
|
||||
// 2) are you shooting? -> stop shooting, you've lost your target
|
||||
if (info.isShooting() || info.isSecondaryShooting()) {
|
||||
getAct().act(new StopShooting());
|
||||
}
|
||||
|
||||
// 3) are you being shot? -> go to HIT (turn around - try to find your enemy)
|
||||
if (senses.isBeingDamaged()) {
|
||||
this.stateHit();
|
||||
return;
|
||||
}
|
||||
|
||||
// 4) have you got enemy to pursue? -> go to the last position of enemy
|
||||
if (enemy != null && shouldPursue && weaponry.hasLoadedWeapon()) { // !enemy.isVisible() because of 2)
|
||||
this.statePursue();
|
||||
return;
|
||||
}
|
||||
|
||||
// 5) are you hurt? -> get yourself some medKit
|
||||
if (shouldCollectHealth && info.getHealth() < healthLevel) {
|
||||
this.stateMedKit();
|
||||
return;
|
||||
}
|
||||
|
||||
// 6) if nothing ... run around items
|
||||
stateRunAroundItems();
|
||||
}
|
||||
|
||||
//////////////////
|
||||
// STATE ENGAGE //
|
||||
//////////////////
|
||||
protected boolean runningToPlayer = false;
|
||||
|
||||
/**
|
||||
* Fired when bot see any enemy. <ol> <li> if enemy that was attacked last
|
||||
* time is not visible than choose new enemy <li> if enemy is reachable and the bot is far - run to him
|
||||
* <li> otherwise - stand still (kind a silly, right? :-)
|
||||
* </ol>
|
||||
*/
|
||||
protected void stateEngage() {
|
||||
//log.info("Decision is: ENGAGE");
|
||||
//config.setName("Hunter [ENGAGE]");
|
||||
|
||||
boolean shooting = false;
|
||||
double distance = Double.MAX_VALUE;
|
||||
pursueCount = 0;
|
||||
|
||||
// 1) pick new enemy if the old one has been lost
|
||||
if (enemy == null || !enemy.isVisible()) {
|
||||
// pick new enemy
|
||||
enemy = players.getNearestVisiblePlayer(players.getVisibleEnemies().values());
|
||||
if (enemy == null) {
|
||||
log.info("Can't see any enemies... ???");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// 2) stop shooting if enemy is not visible
|
||||
if (!enemy.isVisible()) {
|
||||
if (info.isShooting() || info.isSecondaryShooting()) {
|
||||
// stop shooting
|
||||
getAct().act(new StopShooting());
|
||||
}
|
||||
runningToPlayer = false;
|
||||
} else {
|
||||
// 2) or shoot on enemy if it is visible
|
||||
distance = info.getLocation().getDistance(enemy.getLocation());
|
||||
if (shoot.shoot(weaponPrefs, enemy) != null) {
|
||||
log.info("Shooting at enemy!!!");
|
||||
shooting = true;
|
||||
}
|
||||
}
|
||||
|
||||
// 3) if enemy is far or not visible - run to him
|
||||
int decentDistance = Math.round(random.nextFloat() * 800) + 200;
|
||||
if (!enemy.isVisible() || !shooting || decentDistance < distance) {
|
||||
if (!runningToPlayer) {
|
||||
navigation.navigate(enemy);
|
||||
runningToPlayer = true;
|
||||
}
|
||||
} else {
|
||||
runningToPlayer = false;
|
||||
navigation.stopNavigation();
|
||||
}
|
||||
|
||||
item = null;
|
||||
}
|
||||
|
||||
///////////////
|
||||
// STATE HIT //
|
||||
///////////////
|
||||
protected void stateHit() {
|
||||
//log.info("Decision is: HIT");
|
||||
bot.getBotName().setInfo("HIT");
|
||||
if (navigation.isNavigating()) {
|
||||
navigation.stopNavigation();
|
||||
item = null;
|
||||
}
|
||||
getAct().act(new Rotate().setAmount(32000));
|
||||
}
|
||||
|
||||
//////////////////
|
||||
// STATE PURSUE //
|
||||
//////////////////
|
||||
/**
|
||||
* State pursue is for pursuing enemy who was for example lost behind a
|
||||
* corner. How it works?: <ol> <li> initialize properties <li> obtain path
|
||||
* to the enemy <li> follow the path - if it reaches the end - set lastEnemy
|
||||
* to null - bot would have seen him before or lost him once for all </ol>
|
||||
*/
|
||||
protected void statePursue() {
|
||||
//log.info("Decision is: PURSUE");
|
||||
++pursueCount;
|
||||
if (pursueCount > 30) {
|
||||
reset();
|
||||
}
|
||||
if (enemy != null) {
|
||||
bot.getBotName().setInfo("PURSUE");
|
||||
navigation.navigate(enemy);
|
||||
item = null;
|
||||
} else {
|
||||
reset();
|
||||
}
|
||||
}
|
||||
protected int pursueCount = 0;
|
||||
|
||||
//////////////////
|
||||
// STATE MEDKIT //
|
||||
//////////////////
|
||||
protected void stateMedKit() {
|
||||
//log.info("Decision is: MEDKIT");
|
||||
Item item = items.getPathNearestSpawnedItem(ItemType.Category.HEALTH);
|
||||
if (item == null) {
|
||||
log.warning("NO HEALTH ITEM TO RUN TO => ITEMS");
|
||||
stateRunAroundItems();
|
||||
} else {
|
||||
bot.getBotName().setInfo("MEDKIT");
|
||||
navigation.navigate(item);
|
||||
this.item = item;
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////
|
||||
// STATE RUN AROUND ITEMS //
|
||||
////////////////////////////
|
||||
protected List<Item> itemsToRunAround = null;
|
||||
|
||||
protected void stateRunAroundItems() {
|
||||
//log.info("Decision is: ITEMS");
|
||||
//config.setName("Hunter [ITEMS]");
|
||||
if (navigation.isNavigatingToItem()) return;
|
||||
|
||||
List<Item> interesting = new ArrayList<Item>();
|
||||
|
||||
// ADD WEAPONS
|
||||
for (ItemType itemType : ItemType.Category.WEAPON.getTypes()) {
|
||||
if (!weaponry.hasLoadedWeapon(itemType)) interesting.addAll(items.getSpawnedItems(itemType).values());
|
||||
}
|
||||
// ADD ARMORS
|
||||
for (ItemType itemType : ItemType.Category.ARMOR.getTypes()) {
|
||||
interesting.addAll(items.getSpawnedItems(itemType).values());
|
||||
}
|
||||
// ADD QUADS
|
||||
interesting.addAll(items.getSpawnedItems(UT2004ItemType.U_DAMAGE_PACK).values());
|
||||
// ADD HEALTHS
|
||||
if (info.getHealth() < 100) {
|
||||
interesting.addAll(items.getSpawnedItems(UT2004ItemType.HEALTH_PACK).values());
|
||||
}
|
||||
|
||||
Item item = MyCollections.getRandom(tabooItems.filter(interesting));
|
||||
if (item == null) {
|
||||
log.warning("NO ITEM TO RUN FOR!");
|
||||
if (navigation.isNavigating()) return;
|
||||
bot.getBotName().setInfo("RANDOM NAV");
|
||||
navigation.navigate(navPoints.getRandomNavPoint());
|
||||
} else {
|
||||
this.item = item;
|
||||
log.info("RUNNING FOR: " + item.getType().getName());
|
||||
bot.getBotName().setInfo("ITEM: " + item.getType().getName() + "");
|
||||
navigation.navigate(item);
|
||||
}
|
||||
}
|
||||
|
||||
////////////////
|
||||
// BOT KILLED //
|
||||
////////////////
|
||||
@Override
|
||||
public void botKilled(BotKilled event) {
|
||||
reset();
|
||||
}
|
||||
|
||||
///////////////////////////////////
|
||||
public static void main(String args[]) throws PogamutException {
|
||||
// starts 3 Hunters at once
|
||||
// note that this is the most easy way to get a bunch of (the same) bots running at the same time
|
||||
new UT2004BotRunner(HunterBot.class, "Hunter").setMain(true).setLogLevel(Level.INFO).startAgents(2);
|
||||
}
|
||||
}
|
602
SitePi/wwwroot/uploads/NavigationBot.java
Normal file
602
SitePi/wwwroot/uploads/NavigationBot.java
Normal file
@ -0,0 +1,602 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
import java.util.logging.Level;
|
||||
|
||||
import cz.cuni.amis.introspection.java.JProp;
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.IPathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.agent.navigation.PathExecutorState;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.EventListener;
|
||||
import cz.cuni.amis.pogamut.base.utils.guice.AgentScoped;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.sensor.NavPoints;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.module.utils.TabooSet;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.IUT2004Navigation;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.UT2004Navigation;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.UT2004PathAutoFixer;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.UT2004PathExecutorStuckState;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.astar.UT2004AStar;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.floydwarshall.FloydWarshallMap;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.navmesh.NavMeshModule;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004BotModuleController;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Initialize;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotKilled;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ConfigChange;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.InitedMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Item;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ItemPickedUp;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.NavPoint;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Player;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Self;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UT2004BotRunner;
|
||||
import cz.cuni.amis.utils.collections.MyCollections;
|
||||
import cz.cuni.amis.utils.exception.PogamutException;
|
||||
import cz.cuni.amis.utils.flag.FlagListener;
|
||||
|
||||
/**
|
||||
* Example of Simple Pogamut bot, that randomly walks around the map.
|
||||
*
|
||||
* <p><p>
|
||||
* Bot is able to handle movers as well as teleporters.
|
||||
*
|
||||
* <p><p>
|
||||
* It also implements player-following, that is, if it sees a player,
|
||||
* it will start to navigate to it.
|
||||
*
|
||||
* <p><p>
|
||||
* We recommend you to try it on map DM-1on1-Albatross or CTF-LostFaith or DM-Flux2.
|
||||
*
|
||||
* <p><p>
|
||||
* This bot also contains an example of {@link TabooSet} usage.
|
||||
*
|
||||
* <p><p>
|
||||
* Bot also instantiates {@link UT2004PathAutoFixer} that automatically removes bad-edges
|
||||
* from navigation graph of UT2004. Note that Pogamut bot's cannot achieve 100% safe navigation
|
||||
* inside UT2004 maps mainly due to edges that does not contain enough information on how
|
||||
* to travel them, we're trying our best, but some edges inside navigation graph exported
|
||||
* from UT2004 cannot be traveled with our current implementation.
|
||||
*
|
||||
* <p><p>
|
||||
* You may control the way the bot informs you about its decisions via {@link ${symbol_pound}shouldLog} and {@link ${symbol_pound}shouldSpeak} flags.
|
||||
*
|
||||
* <p><p>
|
||||
* We advise to change chat settings within UT2004 via ESCAPE -> Settings -> HUD -> Max. Chat Count -> set to 8 (max).
|
||||
*
|
||||
* @author Rudolf Kadlec aka ik
|
||||
* @author Jakub Gemrot aka Jimmy
|
||||
*/
|
||||
@AgentScoped
|
||||
public class NavigationBot extends UT2004BotModuleController {
|
||||
|
||||
/**
|
||||
* Taboo set is working as "black-list", that is you might add some
|
||||
* NavPoints to it for a certain time, marking them as "unavailable".
|
||||
*/
|
||||
protected TabooSet<NavPoint> tabooNavPoints;
|
||||
|
||||
/**
|
||||
* Current navigation point we're navigating to.
|
||||
*/
|
||||
protected NavPoint targetNavPoint;
|
||||
|
||||
/**
|
||||
* Path auto fixer watches for navigation failures and if some navigation
|
||||
* link is found to be unwalkable, it removes it from underlying navigation
|
||||
* graph.
|
||||
*
|
||||
* Note that UT2004 navigation graphs are some times VERY stupid or contains
|
||||
* VERY HARD TO FOLLOW links...
|
||||
*/
|
||||
protected UT2004PathAutoFixer autoFixer;
|
||||
|
||||
/**
|
||||
* Standard {@link UT2004BotModuleController${symbol_pound}getNavigation()} is using {@link FloydWarshallMap} to find the path.
|
||||
* <p><p>
|
||||
* This {@link UT2004Navigation} is initialized using {@link UT2004BotModuleController${symbol_pound}getAStar()} and can be used to confirm, that
|
||||
* {@link UT2004AStar} is working in the map.
|
||||
*/
|
||||
protected UT2004Navigation navigationAStar;
|
||||
|
||||
/**
|
||||
* {@link NavigationBot${symbol_pound}talking} state.
|
||||
*/
|
||||
protected int talking;
|
||||
|
||||
/**
|
||||
* Whether to use {@link ${symbol_pound}navigationAStar} and {@link UT2004AStar} (== true).
|
||||
* <p><p>
|
||||
* Can be configured from NetBeans plugin during runtime.
|
||||
*/
|
||||
@JProp
|
||||
public boolean useAStar = false;
|
||||
|
||||
/**
|
||||
* Whether to use {@link ${symbol_pound}nmNav} or standard {@link UT2004BotModuleController${symbol_pound}getNavigation()}.
|
||||
* <p><p>
|
||||
* Can be configured from NetBeans plugin during runtime.
|
||||
* <p><p>
|
||||
* Note that you must have corresponding .navmesh file for a current played map within directory ./navmesh, more info available at {@link NavMeshModule}.
|
||||
* <p><p>
|
||||
* Note that navigation bot comes with only three navmeshes DM-TrainingDay, DM-1on1-Albatross and DM-Flux2 (see ./navmesh folder within the project folder).
|
||||
*/
|
||||
@JProp
|
||||
public boolean useNavMesh = false;
|
||||
|
||||
/**
|
||||
* Whether we should draw the navmesh before we start running using {@link ${symbol_pound}nmNav} or standard {@link UT2004BotModuleController${symbol_pound}getNavigation()}.
|
||||
* <p><p>
|
||||
* Can be configured from NetBeans plugin during runtime.
|
||||
*/
|
||||
@JProp
|
||||
public boolean drawNavMesh = true;
|
||||
|
||||
/**
|
||||
* Whether we should speak using in game communication within {@link ${symbol_pound}say(String)}.
|
||||
*/
|
||||
public boolean shouldSpeak = true;
|
||||
|
||||
/**
|
||||
* Whether to LOG messages within {@link ${symbol_pound}say(String)}.
|
||||
*/
|
||||
public boolean shouldLog = false;
|
||||
|
||||
/**
|
||||
* What log level to use.
|
||||
*/
|
||||
public Level navigationLogLevel = Level.WARNING;
|
||||
|
||||
/**
|
||||
* Here we will store either {@link UT2004BotModuleController${symbol_pound}getNavigation()} or {@link ${symbol_pound}navigationAStar} according to {@link ${symbol_pound}useAStar}.
|
||||
*/
|
||||
protected IUT2004Navigation navigationToUse;
|
||||
|
||||
private boolean navMeshDrawn = false;
|
||||
|
||||
private int waitForMesh;
|
||||
|
||||
private double waitingForMesh;
|
||||
|
||||
private boolean offMeshLinksDrawn = false;
|
||||
|
||||
private int waitForOffMeshLinks;
|
||||
|
||||
private double waitingForOffMeshLinks;
|
||||
|
||||
/**
|
||||
* Here we can modify initializing command for our bot.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Initialize getInitializeCommand() {
|
||||
return new Initialize().setName("NavigationBot");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void mapInfoObtained() {
|
||||
// YOU CAN USE navBuilder IN HERE
|
||||
|
||||
// IN WHICH CASE YOU SHOULD UNCOMMENT FOLLOWING LINE AFTER EVERY CHANGE
|
||||
navMeshModule.setReloadNavMesh(true); // tells NavMesh to reconstruct OffMeshPoints
|
||||
}
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public void botInitialized(GameInfo gameInfo, ConfigChange config, InitedMessage init) {
|
||||
// initialize taboo set where we store temporarily unavailable navpoints
|
||||
tabooNavPoints = new TabooSet<NavPoint>(bot);
|
||||
|
||||
// auto-removes wrong navigation links between navpoints
|
||||
autoFixer = new UT2004PathAutoFixer(bot, navigation.getPathExecutor(), fwMap, aStar, navBuilder);
|
||||
|
||||
// IMPORTANT
|
||||
// adds a listener to the path executor for its state changes, it will allow you to
|
||||
// react on stuff like "PATH TARGET REACHED" or "BOT STUCK"
|
||||
navigation.getPathExecutor().getState().addStrongListener(new FlagListener<IPathExecutorState>() {
|
||||
|
||||
@Override
|
||||
public void flagChanged(IPathExecutorState changedValue) {
|
||||
pathExecutorStateChange(changedValue);
|
||||
}
|
||||
});
|
||||
|
||||
nmNav.getPathExecutor().getState().addStrongListener(new FlagListener<IPathExecutorState>() {
|
||||
|
||||
@Override
|
||||
public void flagChanged(IPathExecutorState changedValue) {
|
||||
pathExecutorStateChange(changedValue);
|
||||
}
|
||||
});
|
||||
|
||||
navigationAStar = new UT2004Navigation(bot, navigation.getPathExecutor(), aStar, navigation.getBackToNavGraph(), navigation.getRunStraight());
|
||||
navigationAStar.getLog().setLevel(navigationLogLevel);
|
||||
|
||||
navigation.getLog().setLevel(navigationLogLevel);
|
||||
|
||||
nmNav.setLogLevel(navigationLogLevel);
|
||||
}
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@Override
|
||||
public void botFirstSpawn(GameInfo gameInfo, ConfigChange config, InitedMessage init, Self self) {
|
||||
// receive logs from the navigation so you can get a grasp on how it is working
|
||||
//navigation.getPathExecutor().getLog().setLevel(Level.ALL);
|
||||
//nmNav.setLogLevel(Level.ALL);
|
||||
//navigationAStar.getPathExecutor().getLog().setLevel(Level.ALL);
|
||||
}
|
||||
|
||||
/**
|
||||
* This method is called only once right before actual logic() method is
|
||||
* called for the first time.
|
||||
*/
|
||||
@Override
|
||||
public void beforeFirstLogic() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Main method that controls the bot - makes decisions what to do next. It
|
||||
* is called iteratively by Pogamut engine every time a synchronous batch
|
||||
* from the environment is received. This is usually 4 times per second - it
|
||||
* is affected by visionTime variable, that can be adjusted in GameBots ini
|
||||
* file in UT2004/System folder.
|
||||
*/
|
||||
@Override
|
||||
public void logic() {
|
||||
// mark that another logic iteration has began
|
||||
say("--- Logic iteration ---");
|
||||
|
||||
// decide which navigation to use
|
||||
chooseNavigationToUse();
|
||||
if (navigationToUse == nmNav && drawNavMesh) {
|
||||
if (!drawNavMesh()) return;
|
||||
if (!drawOffMeshLinks()) return;
|
||||
}
|
||||
|
||||
if (players.canSeePlayers() || navigationToUse.getCurrentTargetPlayer() != null) {
|
||||
// we can see some player / is navigating to some point where we lost the player from sight
|
||||
// => navigate to player
|
||||
handlePlayerNavigation();
|
||||
} else {
|
||||
// no player can be seen
|
||||
// => navigate to navpoint
|
||||
handleNavPointNavigation();
|
||||
}
|
||||
}
|
||||
|
||||
private void chooseNavigationToUse() {
|
||||
if (useAStar) {
|
||||
if (navigationToUse != navigationAStar) {
|
||||
say("Using UT2004AStar to find path.");
|
||||
if (navigationToUse != null) navigationToUse.stopNavigation();
|
||||
navigationToUse = navigationAStar;
|
||||
info.getBotName().setInfo("UT2004-ASTAR");
|
||||
}
|
||||
} else
|
||||
if (useNavMesh) {
|
||||
if (nmNav.isAvailable()) {
|
||||
if (navigationToUse != nmNav) {
|
||||
say("Using NavMesh for navigation.");
|
||||
if (navigationToUse != null) navigationToUse.stopNavigation();
|
||||
navigationToUse = nmNav;
|
||||
info.getBotName().setInfo("NAVMESH");
|
||||
}
|
||||
} else {
|
||||
log.warning("NavMesh not available! See startup log for more details.");
|
||||
}
|
||||
}
|
||||
if (navigationToUse == null || (!useAStar && !useNavMesh)) {
|
||||
if (navigationToUse != navigation) {
|
||||
say("Using FloydWarshallMap to find path.");
|
||||
if (navigationToUse != null) navigationToUse.stopNavigation();
|
||||
navigationToUse = navigation;
|
||||
info.getBotName().setInfo("FW");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void handlePlayerNavigation() {
|
||||
if (navigationToUse.isNavigating() && navigationToUse.getCurrentTargetPlayer() != null) {
|
||||
// WE'RE NAVIGATING TO SOME PLAYER
|
||||
logNavigation();
|
||||
return;
|
||||
}
|
||||
|
||||
// NAVIGATION HAS STOPPED ...
|
||||
// => we need to choose another player to navigate to
|
||||
|
||||
Player player = players.getNearestVisiblePlayer();
|
||||
if (player == null) {
|
||||
// NO PLAYERS AT SIGHT
|
||||
// => navigate to random navpoint
|
||||
handleNavPointNavigation();
|
||||
return;
|
||||
}
|
||||
|
||||
// CHECK DISTANCE TO THE PLAYER ...
|
||||
if (info.getLocation().getDistance(player.getLocation()) < UT2004Navigation.AT_PLAYER) {
|
||||
// PLAYER IS NEXT TO US...
|
||||
// => talk to player
|
||||
talkTo(player);
|
||||
return;
|
||||
}
|
||||
|
||||
navigationToUse.navigate(player);
|
||||
logNavigation();
|
||||
}
|
||||
|
||||
private void handleNavPointNavigation() {
|
||||
if (navigationToUse.isNavigatingToNavPoint()) {
|
||||
// IS TARGET CLOSE & NEXT TARGET NOT SPECIFIED?
|
||||
while (navigationToUse.getContinueTo() == null && navigationToUse.getRemainingDistance() < 400) {
|
||||
// YES, THERE IS NO "next-target" SET AND WE'RE ABOUT TO REACH OUR TARGET!
|
||||
NavPoint nextNavPoint = getRandomNavPoint();
|
||||
say("EXTENDING THE PATH: " + NavPoints.describe(nextNavPoint));
|
||||
navigationToUse.setContinueTo(nextNavPoint);
|
||||
// note that it is WHILE because navigation may immediately eat up "next target" and next target may be actually still too close!
|
||||
}
|
||||
|
||||
// WE'RE NAVIGATING TO SOME NAVPOINT
|
||||
logNavigation();
|
||||
return;
|
||||
}
|
||||
|
||||
// NAVIGATION HAS STOPPED ...
|
||||
// => we need to choose another navpoint to navigate to
|
||||
// => possibly follow some players ...
|
||||
|
||||
targetNavPoint = getRandomNavPoint();
|
||||
if (targetNavPoint == null) {
|
||||
log.severe("COULD NOT CHOOSE ANY NAVIGATION POINT TO RUN TO!!!");
|
||||
if (world.getAll(NavPoint.class).size() == 0) {
|
||||
log.severe("world.getAll(NavPoint.class).size() == 0, there are no navigation ponits to choose from! Is exporting of nav points enabled in GameBots2004.ini inside UT2004?");
|
||||
}
|
||||
config.setName("NavigationBot [CRASHED]");
|
||||
return;
|
||||
}
|
||||
|
||||
talking = 0;
|
||||
|
||||
say("CHOOSING FIRST NAVPOINT TO RUN TO: " + NavPoints.describe(targetNavPoint));
|
||||
navigationToUse.navigate(targetNavPoint);
|
||||
logNavigation();
|
||||
}
|
||||
|
||||
private void logNavigation() {
|
||||
// log how many navpoints & items the bot knows about and which is visible
|
||||
if (navigationToUse.getCurrentTargetPlayer() != null) {
|
||||
say("-> " + NavPoints.describe(navigationToUse.getCurrentTargetPlayer()));
|
||||
} else {
|
||||
say("-> " + NavPoints.describe(navigationToUse.getCurrentTarget()));
|
||||
}
|
||||
int pathLeftSize = navigationToUse.getPathExecutor().getPath() == null ? 0 : navigationToUse.getPathExecutor().getPath().size() - navigationToUse.getPathExecutor().getPathElementIndex();
|
||||
say("Path points left: " + pathLeftSize);
|
||||
say("Remaining distance: " + navigationToUse.getRemainingDistance());
|
||||
say("Visible navpoints: " + world.getAllVisible(NavPoint.class).size() + " / " + world.getAll(NavPoint.class).size());
|
||||
say("Visible items: " + items.getVisibleItems().values() + " / " + world.getAll(Item.class).size());
|
||||
say("Visible players: " + players.getVisiblePlayers().size());
|
||||
}
|
||||
|
||||
private void talkTo(Player player) {
|
||||
// FACE THE PLAYER
|
||||
move.turnTo(player);
|
||||
|
||||
// SEND MESSAGES
|
||||
switch (talking) {
|
||||
case 0:
|
||||
say("Hi!");
|
||||
break;
|
||||
case 4:
|
||||
say("Howdy!");
|
||||
break;
|
||||
case 10:
|
||||
say("I'm NavigationBot made to fool around and test Pogamut's navigation stuff!");
|
||||
break;
|
||||
case 18:
|
||||
say("My work is extremely important.");
|
||||
break;
|
||||
case 24:
|
||||
say("So do not interrupt me, ok?");
|
||||
break;
|
||||
case 26:
|
||||
if (random.nextDouble() > 0.5) {
|
||||
move.jump();
|
||||
}
|
||||
break;
|
||||
case 40:
|
||||
say(getRandomLogoutMessage());
|
||||
break;
|
||||
}
|
||||
|
||||
++talking;
|
||||
if (talking > 40) {
|
||||
talking = 25;
|
||||
}
|
||||
}
|
||||
|
||||
private String getRandomLogoutMessage() {
|
||||
switch (random.nextInt(8)) {
|
||||
case 0:
|
||||
return "I would appriciate if you log out or switch to SPECTATE mode.";
|
||||
case 1:
|
||||
return "Would you please log out or switch to SPECTATE mode.";
|
||||
case 2:
|
||||
return "Just log out, will ya?";
|
||||
case 3:
|
||||
return "As I've said, I'M SOMEONE, so log out, ok?";
|
||||
case 4:
|
||||
return "I can see you don't get it... LOGOUT! OK!";
|
||||
case 5:
|
||||
return "I hate when humans are so clueless... just press ESCAPE key and press Spectate button, that's all I want!";
|
||||
case 6:
|
||||
return "I guess you do not know how to switch to spectate mode, right? Just press ESCAPE key and press Spectate button";
|
||||
default:
|
||||
return "AHAHAHAYYYAAAA!";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean drawNavMesh() {
|
||||
if (!navMeshDrawn) {
|
||||
navMeshDrawn = true;
|
||||
say("Drawing NavMesh...");
|
||||
navMeshModule.getNavMeshDraw().clearAll();
|
||||
navMeshModule.getNavMeshDraw().draw(true, false);
|
||||
say("Okey, drawing commands issued, now we have to wait a bit till it gets drawn completely...");
|
||||
|
||||
waitForMesh = navMeshModule.getNavMesh().getPolys().size() / 35;
|
||||
waitingForMesh = -info.getTimeDelta();
|
||||
}
|
||||
|
||||
if (waitForMesh > 0) {
|
||||
waitForMesh -= info.getTimeDelta();
|
||||
waitingForMesh += info.getTimeDelta();
|
||||
if (waitingForMesh > 2) {
|
||||
waitingForMesh = 0;
|
||||
say(((int)Math.round(waitForMesh)) + "s...");
|
||||
}
|
||||
if (waitForMesh > 0) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
private boolean drawOffMeshLinks() {
|
||||
if (!offMeshLinksDrawn) {
|
||||
offMeshLinksDrawn = true;
|
||||
|
||||
if (navMeshModule.getNavMesh().getOffMeshPoints().size() == 0) {
|
||||
say("Ha! There are no off-mesh points / links within this map!");
|
||||
return true;
|
||||
}
|
||||
|
||||
say("Drawing OffMesh Links...");
|
||||
navMeshModule.getNavMeshDraw().draw(false, true);
|
||||
say("Okey, drawing commands issued, now we have to wait a bit till it gets drawn completely...");
|
||||
waitForOffMeshLinks = navMeshModule.getNavMesh().getOffMeshPoints().size() / 10;
|
||||
waitingForOffMeshLinks = -info.getTimeDelta();
|
||||
}
|
||||
|
||||
if (waitForOffMeshLinks > 0) {
|
||||
waitForOffMeshLinks -= info.getTimeDelta();
|
||||
waitingForOffMeshLinks += info.getTimeDelta();
|
||||
if (waitingForOffMeshLinks > 2) {
|
||||
waitingForOffMeshLinks = 0;
|
||||
say(((int)Math.round(waitForOffMeshLinks)) + "s...");
|
||||
}
|
||||
if (waitForOffMeshLinks > 0) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
private void say(String text) {
|
||||
if (shouldSpeak) {
|
||||
body.getCommunication().sendGlobalTextMessage(text);
|
||||
}
|
||||
if (shouldLog) {
|
||||
say(text);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Called each time our bot die. Good for reseting all bot state dependent
|
||||
* variables.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
public void botKilled(BotKilled event) {
|
||||
navigation.stopNavigation();
|
||||
}
|
||||
|
||||
/**
|
||||
* Path executor has changed its state (note that {@link UT2004BotModuleController${symbol_pound}getPathExecutor()}
|
||||
* is internally used by
|
||||
* {@link UT2004BotModuleController${symbol_pound}getNavigation()} as well!).
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
protected void pathExecutorStateChange(IPathExecutorState event) {
|
||||
switch (event.getState()) {
|
||||
case PATH_COMPUTATION_FAILED:
|
||||
// if path computation fails to whatever reason, just try another navpoint
|
||||
// taboo bad navpoint for 3 minutes
|
||||
tabooNavPoints.add(targetNavPoint, 180);
|
||||
break;
|
||||
|
||||
case TARGET_REACHED:
|
||||
// taboo reached navpoint for 3 minutes
|
||||
tabooNavPoints.add(targetNavPoint, 180);
|
||||
break;
|
||||
|
||||
case STUCK:
|
||||
UT2004PathExecutorStuckState stuck = (UT2004PathExecutorStuckState)event;
|
||||
if (stuck.isGlobalTimeout()) {
|
||||
say("UT2004PathExecutor GLOBAL TIMEOUT!");
|
||||
} else {
|
||||
say(stuck.getStuckDetector() + " reported STUCK!");
|
||||
}
|
||||
if (stuck.getLink() == null) {
|
||||
say("STUCK LINK is NOT AVAILABLE!");
|
||||
} else {
|
||||
say("Bot has stuck while running from " + stuck.getLink().getFromNavPoint().getId() + " -> " + stuck.getLink().getToNavPoint().getId());
|
||||
}
|
||||
|
||||
// the bot has stuck! ... target nav point is unavailable currently
|
||||
tabooNavPoints.add(targetNavPoint, 60);
|
||||
break;
|
||||
|
||||
case STOPPED:
|
||||
// path execution has stopped
|
||||
targetNavPoint = null;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Randomly picks some navigation point to head to.
|
||||
*
|
||||
* @return randomly choosed navpoint
|
||||
*/
|
||||
protected NavPoint getRandomNavPoint() {
|
||||
say("Picking new target navpoint.");
|
||||
|
||||
// choose one feasible navpoint (== not belonging to tabooNavPoints) randomly
|
||||
NavPoint chosen = MyCollections.getRandomFiltered(getWorldView().getAll(NavPoint.class).values(), tabooNavPoints);
|
||||
|
||||
if (chosen != null) {
|
||||
return chosen;
|
||||
}
|
||||
|
||||
log.warning("All navpoints are tabooized at this moment, choosing navpoint randomly!");
|
||||
|
||||
// ok, all navpoints have been visited probably, try to pick one at random
|
||||
return MyCollections.getRandom(getWorldView().getAll(NavPoint.class).values());
|
||||
}
|
||||
|
||||
public static void main(String args[]) throws PogamutException {
|
||||
// wrapped logic for bots executions, suitable to run single bot in single JVM
|
||||
|
||||
// you can set the log level to FINER to see (almost) all logs
|
||||
// that describes decision making behind movement of the bot as well as incoming environment events
|
||||
// however note that in NetBeans this will cause your bot to lag heavilly (in Eclipse it is ok)
|
||||
new UT2004BotRunner(NavigationBot.class, "NavigationBot").setMain(true).setLogLevel(Level.WARNING).startAgent();
|
||||
}
|
||||
}
|
272
SitePi/wwwroot/uploads/RaycastingBot.java
Normal file
272
SitePi/wwwroot/uploads/RaycastingBot.java
Normal file
@ -0,0 +1,272 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
import javax.vecmath.Vector3d;
|
||||
|
||||
import cz.cuni.amis.introspection.java.JProp;
|
||||
import cz.cuni.amis.pogamut.base.utils.guice.AgentScoped;
|
||||
import cz.cuni.amis.pogamut.ut2004.agent.navigation.navmesh.LevelGeometryModule;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004BotModuleController;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Configuration;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.RemoveRay;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.AutoTraceRay;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ConfigChange;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.InitedMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UT2004BotRunner;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UnrealUtils;
|
||||
import cz.cuni.amis.utils.exception.PogamutException;
|
||||
import cz.cuni.amis.utils.flag.FlagListener;
|
||||
|
||||
/**
|
||||
* Example of Simple Pogamut bot, that randomly walks around the map. Bot is
|
||||
* incapable of handling movers so far.
|
||||
*
|
||||
* <p><p>
|
||||
* The crucial method to read
|
||||
* through is {@link RaycastingBot${symbol_pound}botInitialized(GameInfo, ConfigChange, InitedMessage)},
|
||||
* it will show you how to set up ray-casting.
|
||||
*
|
||||
* <p><p>
|
||||
* We recommend you to try this bot on DM-TrainingDay or DM-Albatross or DM-Flux2.
|
||||
*
|
||||
* <p><p>
|
||||
* Note that this is a bit deprecated way to do raycasting as we have more advanced approach via "geometry-at-client", see {@link LevelGeometryModule}
|
||||
* and checkout svn://artemis.ms.mff.cuni.cz/pogamut/trunk/project/Main/PogamutUT2004Examples/35-ManualBot that contains hints how to do raycasting client-side.
|
||||
*
|
||||
*
|
||||
* @author Ondrej Burkert
|
||||
* @author Rudolf Kadlec aka ik
|
||||
* @author Jakub Gemrot aka Jimmy
|
||||
*/
|
||||
@AgentScoped
|
||||
@Deprecated
|
||||
public class RaycastingBot extends UT2004BotModuleController {
|
||||
|
||||
// Constants for rays' ids. It is allways better to store such values
|
||||
// in constants instead of using directly strings on multiple places of your
|
||||
// source code
|
||||
protected static final String FRONT = "frontRay";
|
||||
protected static final String LEFT45 = "left45Ray";
|
||||
protected static final String LEFT90 = "left90Ray";
|
||||
protected static final String RIGHT45 = "right45Ray";
|
||||
protected static final String RIGHT90 = "right90Ray";
|
||||
|
||||
private AutoTraceRay left, front, right;
|
||||
|
||||
/**
|
||||
* Flag indicating that the bot has been just executed.
|
||||
*/
|
||||
private boolean first = true;
|
||||
private boolean raysInitialized = false;
|
||||
/**
|
||||
* Whether the left45 sensor signalizes the collision. (Computed in the
|
||||
* doLogic()) <p><p> Using {@link RaycastingBot${symbol_pound}LEFT45} as the key for the
|
||||
* ray.
|
||||
*/
|
||||
@JProp
|
||||
private boolean sensorLeft45 = false;
|
||||
/**
|
||||
* Whether the right45 sensor signalizes the collision. (Computed in the
|
||||
* doLogic()) <p><p> Using {@link RaycastingBot${symbol_pound}RIGHT45} as the key for the
|
||||
* ray.
|
||||
*/
|
||||
@JProp
|
||||
private boolean sensorRight45 = false;
|
||||
/**
|
||||
* Whether the front sensor signalizes the collision. (Computed in the
|
||||
* doLogic()) <p><p> Using {@link RaycastingBot${symbol_pound}FRONT} as the key for the
|
||||
* ray.
|
||||
*/
|
||||
@JProp
|
||||
private boolean sensorFront = false;
|
||||
/**
|
||||
* Whether the bot is moving. (Computed in the doLogic())
|
||||
*/
|
||||
@JProp
|
||||
private boolean moving = false;
|
||||
/**
|
||||
* Whether any of the sensor signalize the collision. (Computed in the
|
||||
* doLogic())
|
||||
*/
|
||||
@JProp
|
||||
private boolean sensor = false;
|
||||
/**
|
||||
* How much time should we wait for the rotation to finish (milliseconds).
|
||||
*/
|
||||
@JProp
|
||||
private int turnSleep = 250;
|
||||
/**
|
||||
* How fast should we move? Interval <0, 1>.
|
||||
*/
|
||||
private float moveSpeed = 0.6f;
|
||||
/**
|
||||
* Small rotation (degrees).
|
||||
*/
|
||||
@JProp
|
||||
private int smallTurn = 30;
|
||||
/**
|
||||
* Big rotation (degrees).
|
||||
*/
|
||||
@JProp
|
||||
private int bigTurn = 90;
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@Override
|
||||
public void botInitialized(GameInfo info, ConfigChange currentConfig, InitedMessage init) {
|
||||
// initialize rays for raycasting
|
||||
final int rayLength = (int) (UnrealUtils.CHARACTER_COLLISION_RADIUS * 10);
|
||||
// settings for the rays
|
||||
boolean fastTrace = true; // perform only fast trace == we just need true/false information
|
||||
boolean floorCorrection = false; // provide floor-angle correction for the ray (when the bot is running on the skewed floor, the ray gets rotated to match the skew)
|
||||
boolean traceActor = false; // whether the ray should collid with other actors == bots/players as well
|
||||
|
||||
// 1. remove all previous rays, each bot starts by default with three
|
||||
// rays, for educational purposes we will set them manually
|
||||
getAct().act(new RemoveRay("All"));
|
||||
|
||||
// 2. create new rays
|
||||
raycasting.createRay(LEFT45, new Vector3d(1, -1, 0), rayLength, fastTrace, floorCorrection, traceActor);
|
||||
raycasting.createRay(FRONT, new Vector3d(1, 0, 0), rayLength, fastTrace, floorCorrection, traceActor);
|
||||
raycasting.createRay(RIGHT45, new Vector3d(1, 1, 0), rayLength, fastTrace, floorCorrection, traceActor);
|
||||
// note that we will use only three of them, so feel free to experiment with LEFT90 and RIGHT90 for yourself
|
||||
raycasting.createRay(LEFT90, new Vector3d(0, -1, 0), rayLength, fastTrace, floorCorrection, traceActor);
|
||||
raycasting.createRay(RIGHT90, new Vector3d(0, 1, 0), rayLength, fastTrace, floorCorrection, traceActor);
|
||||
|
||||
|
||||
// register listener called when all rays are set up in the UT engine
|
||||
raycasting.getAllRaysInitialized().addListener(new FlagListener<Boolean>() {
|
||||
|
||||
public void flagChanged(Boolean changedValue) {
|
||||
// once all rays were initialized store the AutoTraceRay objects
|
||||
// that will come in response in local variables, it is just
|
||||
// for convenience
|
||||
left = raycasting.getRay(LEFT45);
|
||||
front = raycasting.getRay(FRONT);
|
||||
right = raycasting.getRay(RIGHT45);
|
||||
}
|
||||
});
|
||||
// have you noticed the FlagListener interface? The Pogamut is often using {@link Flag} objects that
|
||||
// wraps some iteresting values that user might respond to, i.e., whenever the flag value is changed,
|
||||
// all its listeners are informed
|
||||
|
||||
// 3. declare that we are not going to setup any other rays, so the 'raycasting' object may know what "all" is
|
||||
raycasting.endRayInitSequence();
|
||||
|
||||
// change bot's default speed
|
||||
config.setSpeedMultiplier(moveSpeed);
|
||||
|
||||
// IMPORTANT:
|
||||
// The most important thing is this line that ENABLES AUTO TRACE functionality,
|
||||
// without ".setAutoTrace(true)" the AddRay command would be useless as the bot won't get
|
||||
// trace-lines feature activated
|
||||
getAct().act(new Configuration().setDrawTraceLines(true).setAutoTrace(true));
|
||||
|
||||
// FINAL NOTE: the ray initialization must be done inside botInitialized method or later on inside
|
||||
// botSpawned method or anytime during doLogic method
|
||||
}
|
||||
|
||||
/**
|
||||
* Main method that controls the bot.
|
||||
*
|
||||
* @throws cz.cuni.amis.pogamut.base.exceptions.PogamutException
|
||||
*/
|
||||
@Override
|
||||
public void logic() throws PogamutException {
|
||||
// mark that another logic iteration has began
|
||||
log.info("--- Logic iteration ---");
|
||||
|
||||
// if the rays are not initialized yet, do nothing and wait for their initialization
|
||||
if (!raycasting.getAllRaysInitialized().getFlag()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// once the rays are up and running, move according to them
|
||||
|
||||
sensorFront = front.isResult();
|
||||
sensorLeft45 = left.isResult();
|
||||
sensorRight45 = right.isResult();
|
||||
|
||||
// is any of the sensor signalig?
|
||||
sensor = sensorFront || sensorLeft45 || sensorRight45;
|
||||
|
||||
if (!sensor) {
|
||||
// no sensor are signalizes - just proceed with forward movement
|
||||
goForward();
|
||||
return;
|
||||
}
|
||||
|
||||
// some sensor/s is/are signaling
|
||||
|
||||
// if we're moving
|
||||
if (moving) {
|
||||
// stop it, we have to turn probably
|
||||
move.stopMovement();
|
||||
moving = false;
|
||||
}
|
||||
|
||||
// according to the signals, take action...
|
||||
// 8 cases that might happen follows
|
||||
if (sensorFront) {
|
||||
if (sensorLeft45) {
|
||||
if (sensorRight45) {
|
||||
// LEFT45, RIGHT45, FRONT are signaling
|
||||
move.turnHorizontal(bigTurn);
|
||||
} else {
|
||||
// LEFT45, FRONT45 are signaling
|
||||
move.turnHorizontal(smallTurn);
|
||||
}
|
||||
} else {
|
||||
if (sensorRight45) {
|
||||
// RIGHT45, FRONT are signaling
|
||||
move.turnHorizontal(-smallTurn);
|
||||
} else {
|
||||
// FRONT is signaling
|
||||
move.turnHorizontal(smallTurn);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (sensorLeft45) {
|
||||
if (sensorRight45) {
|
||||
// LEFT45, RIGHT45 are signaling
|
||||
goForward();
|
||||
} else {
|
||||
// LEFT45 is signaling
|
||||
move.turnHorizontal(smallTurn);
|
||||
}
|
||||
} else {
|
||||
if (sensorRight45) {
|
||||
// RIGHT45 is signaling
|
||||
move.turnHorizontal(-smallTurn);
|
||||
} else {
|
||||
// no sensor is signaling
|
||||
goForward();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// HOMEWORK FOR YOU GUYS:
|
||||
// Try to utilize LEFT90 and RIGHT90 sensors and implement wall-following behavior!
|
||||
}
|
||||
|
||||
/**
|
||||
* Simple method that starts continuous movement forward + marking the
|
||||
* situation (i.e., setting {@link RaycastingBot${symbol_pound}moving} to true, which
|
||||
* might be utilized later by the logic).
|
||||
*/
|
||||
protected void goForward() {
|
||||
move.moveContinuos();
|
||||
moving = true;
|
||||
}
|
||||
|
||||
public static void main(String args[]) throws PogamutException {
|
||||
// wrapped logic for bots executions, suitable to run single bot in single JVM
|
||||
new UT2004BotRunner(RaycastingBot.class, "RaycastingBot").setMain(true).startAgent();
|
||||
}
|
||||
}
|
384
SitePi/wwwroot/uploads/ResponsiveBot.java
Normal file
384
SitePi/wwwroot/uploads/ResponsiveBot.java
Normal file
@ -0,0 +1,384 @@
|
||||
|
||||
package com.mycompany.mavenproject1;
|
||||
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.IWorldView;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.event.IWorldEvent;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.event.IWorldEventListener;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.AnnotationListenerRegistrator;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.EventListener;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.ObjectClassEventListener;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.ObjectClassListener;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.ObjectEventListener;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.listener.annotation.ObjectListener;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.object.IWorldObject;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.object.IWorldObjectEvent;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.object.event.WorldObjectDestroyedEvent;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.object.event.WorldObjectFirstEncounteredEvent;
|
||||
import cz.cuni.amis.pogamut.base.communication.worldview.object.event.WorldObjectUpdatedEvent;
|
||||
import cz.cuni.amis.pogamut.base.utils.guice.AgentScoped;
|
||||
import cz.cuni.amis.pogamut.base.utils.math.DistanceUtils;
|
||||
import cz.cuni.amis.pogamut.base3d.worldview.object.Location;
|
||||
import cz.cuni.amis.pogamut.base3d.worldview.object.event.WorldObjectAppearedEvent;
|
||||
import cz.cuni.amis.pogamut.base3d.worldview.object.event.WorldObjectDisappearedEvent;
|
||||
import cz.cuni.amis.pogamut.unreal.communication.messages.UnrealId;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004Bot;
|
||||
import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004BotModuleController;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.Initialize;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotDamaged;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotKilled;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Bumped;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ConfigChange;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.EndMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.InitedMessage;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.NavPoint;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Player;
|
||||
import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Self;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UT2004BotRunner;
|
||||
import cz.cuni.amis.pogamut.ut2004.utils.UnrealUtils;
|
||||
import cz.cuni.amis.utils.exception.PogamutException;
|
||||
|
||||
/**
|
||||
* Example of Simple Pogamut bot, that can listen to some events coming from
|
||||
* the game engine and respond to them appropriately. The logic of the bot is
|
||||
* completely event driven.
|
||||
*
|
||||
* <p><p>
|
||||
* Notice that we're using a special annotations
|
||||
* for various methods, i.e., for the method {@link ResponsiveBot${symbol_pound}bumped(Bumped)}
|
||||
* the annotation {@link EventListener}, for the method {@link ResponsiveBot${symbol_pound}playerAppeared(WorldObjectAppearedEvent)}
|
||||
* we're using {@link ObjectClassEventListener}, etc. You may perceive is as a bit magic as
|
||||
* some methods are called as a response to some event, e.g., the method {@link ResponsiveBot${symbol_pound}bumped(Bumped)}
|
||||
* is called whenever GameBots2004 sends a message {@link Bumped} to the bot.
|
||||
*
|
||||
* <p><p>
|
||||
* How is this possible?
|
||||
*
|
||||
* <p><p>
|
||||
* Well, the {@link UT2004BotModuleController}
|
||||
* is using {@link AnnotationListenerRegistrator} that introspects (via Java
|
||||
* Reflection API) the methods declared by the {@link ResponsiveBot} looking for
|
||||
* annotations: {@link EventListener}, {@link ObjectClassEventListener},
|
||||
* {@link ObjectClassListener}, {@link ObjectEventListener} or {@link ObjectListener}
|
||||
* (I recommend you to read javadoc for all of them) automatically registering a
|
||||
* listener inside {@link ResponsiveBot${symbol_pound}getWorldView()} using one of the
|
||||
* "addListener" methods (e.g. {@link EventListener} annotated method is recalled
|
||||
* from listener added via {@link IWorldView${symbol_pound}addEventListener(java.lang.Class, cz.cuni.amis.pogamut.base.communication.worldview.event.IWorldEventListener)}.
|
||||
* It provides you with a simple way how to create methods that reacts on certain events inside the game.
|
||||
*
|
||||
* <p><p>
|
||||
* WARNING: these annotations works only in THIS class only. If you want other of your classes to have the
|
||||
* same option, you will have to instantiate {@link AnnotationListenerRegistrator} for yourself
|
||||
* within that class.
|
||||
*
|
||||
* <p><p>
|
||||
* We advise you to read through all comments carefully and try to understand
|
||||
* when {@link EventListener} suffices and when you need to use one
|
||||
* of {@link ObjectClassEventListener} /
|
||||
* {@link ObjectClassListener} / {@link ObjectEventListener} / {@link ObjectListener}s.
|
||||
*
|
||||
* <p><p>
|
||||
* The trick is that some messages from GB2004 are {@link IWorldEvent}s only and some of them are {@link IWorldObject}s as well.
|
||||
* For listening {@link IWorldEvent}s only you must use {@link EventListener}, for listening to object updates,
|
||||
* you must use one of {@link ObjectClassEventListener} / {@link ObjectClassListener} / {@link ObjectEventListener} / {@link ObjectListener}s.
|
||||
*
|
||||
* <p><p>
|
||||
* We recommend you to run the bot on DM-TrainingDay map.
|
||||
*
|
||||
* <p><p>
|
||||
* Start the bot and run to it. Note that whenever the bot sees you (you enter bot's field of view}
|
||||
* {@link ResponsiveBot${symbol_pound}playerAppeared(cz.cuni.amis.pogamut.base3d.worldview.object.event.WorldObjectAppearedEvent)} will be triggered
|
||||
* and the bot will greet you.
|
||||
*
|
||||
* <p><p>
|
||||
* Then try to approach very close to the bot and it will ask you "what do you want". See {@link ResponsiveBot${symbol_pound}playerUpdated(cz.cuni.amis.pogamut.base.communication.worldview.object.event.WorldObjectUpdatedEvent) }
|
||||
* event listener method.
|
||||
*
|
||||
* <p><p>
|
||||
* Check out comments inside {@link ResponsiveBot${symbol_pound}gb2004BatchEnd(cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.EndMessage)} message.
|
||||
*
|
||||
* @author Rudolf Kadlec aka ik
|
||||
* @author Jakub Gemrot aka Jimmy
|
||||
*/
|
||||
@AgentScoped
|
||||
public class ResponsiveBot extends UT2004BotModuleController {
|
||||
|
||||
/**
|
||||
* Listener called when someone/something bumps into the bot. The bot
|
||||
* responds by moving in the opposite direction than the bump come from.
|
||||
*
|
||||
* <p><p>
|
||||
* We're using {@link EventListener} here that is registered by the {@link AnnotationListenerRegistrator}
|
||||
* to listen for {@link Bumped} events.
|
||||
*
|
||||
* <p><p>
|
||||
* Notice that {@link Bumped} is {@link IWorldEvent} only, it's not {@link IWorldObject},
|
||||
* thus we're using {@link EventListener}.
|
||||
*/
|
||||
@EventListener(eventClass = Bumped.class)
|
||||
protected void bumped(Bumped event) {
|
||||
// schema of the vector computations
|
||||
//
|
||||
// e<->a<------>t
|
||||
// | | v |
|
||||
// | | target - bot will be heading there
|
||||
// | getLocation()
|
||||
// event.getLocation()
|
||||
|
||||
Location v = event.getLocation().sub(bot.getLocation()).scale(5);
|
||||
Location target = bot.getLocation().sub(v);
|
||||
|
||||
// make the bot to go to the computed location while facing the bump source
|
||||
move.strafeTo(target, event.getLocation());
|
||||
}
|
||||
|
||||
/**
|
||||
* Listener called when a player appears.
|
||||
*
|
||||
* <p><p>
|
||||
* We're using {@link ObjectClassEventListener} here that is registered by the {@link AnnotationListenerRegistrator} to
|
||||
* listen on all {@link WorldObjectAppearedEvent} that happens on any object
|
||||
* of the class {@link Player}.
|
||||
*
|
||||
* <p><p>
|
||||
* I.e., whenever the GameBots2004 sends an
|
||||
* update about arbitrary {@link Player} object in the game notifying us that the
|
||||
* player has become visible (it's {@link Player${symbol_pound}isVisible()} is switched to
|
||||
* true and the {@link WorldObjectAppearedEvent} is generated), this method
|
||||
* is called.
|
||||
*
|
||||
* <p><p>
|
||||
* Notice that {@link Player} implements {@link IWorldObject} thus you CANNOT use
|
||||
* {@link EventListener} to catch events that updates {@link Player} objects.
|
||||
*/
|
||||
@ObjectClassEventListener(eventClass = WorldObjectAppearedEvent.class, objectClass = Player.class)
|
||||
protected void playerAppeared(WorldObjectAppearedEvent<Player> event) {
|
||||
// greet player when he appears
|
||||
body.getCommunication().sendGlobalTextMessage("Hello " + event.getObject().getName() + "!");
|
||||
}
|
||||
/**
|
||||
* Flag indicating whether the player was also close to the bot last time it
|
||||
* was updated.
|
||||
*/
|
||||
protected boolean wasCloseBefore = false;
|
||||
|
||||
/**
|
||||
* Listener called each time a player is updated.
|
||||
*
|
||||
* <p><p>
|
||||
* Again, we're using {@link ObjectClassEventListener}
|
||||
* that is registered by the {@link AnnotationListenerRegistrator} to listen
|
||||
* on all {@link WorldObjectUpdatedEvent} that happens on any object of the
|
||||
* class {@link Player}.
|
||||
*
|
||||
* <p><p>
|
||||
* I.e., whenever the GameBots2004 sends an update
|
||||
* about arbitrary {@link Player} in the game notifying us that some
|
||||
* information about the player has changed (the {@link WorldObjectUpdatedEvent}
|
||||
* is generated), this method is called.
|
||||
*
|
||||
* <p><p>
|
||||
* Again, {@link Player} implements {@link IWorldObject}, thus you CANNOT use
|
||||
* {@link EventListener} annotation to check for events regarding {@link Player}
|
||||
* objects.
|
||||
*/
|
||||
@ObjectClassEventListener(eventClass = WorldObjectUpdatedEvent.class, objectClass = Player.class)
|
||||
protected void playerUpdated(WorldObjectUpdatedEvent<Player> event) {
|
||||
// Check whether the player is closer than 5 bot diameters.
|
||||
// Notice the use of the UnrealUtils class.
|
||||
// It contains many auxiliary constants and methods.
|
||||
Player player = event.getObject();
|
||||
// First player objects are received in HandShake - at that time we don't have Self message yet or players location!!
|
||||
if (player.getLocation() == null || info.getLocation() == null) {
|
||||
return;
|
||||
}
|
||||
if (player.getLocation().getDistance(info.getLocation()) < (UnrealUtils.CHARACTER_COLLISION_RADIUS * 10)) {
|
||||
// If the player wasn't close enough the last time this listener was called,
|
||||
// then ask him what does he want.
|
||||
if (!wasCloseBefore) {
|
||||
body.getCommunication().sendGlobalTextMessage("What do you want " + player.getName() + "?");
|
||||
// Set proximity flag to true.
|
||||
wasCloseBefore = true;
|
||||
}
|
||||
} else {
|
||||
// Otherwise set the proximity flag to false.
|
||||
wasCloseBefore = false;
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Listener that is manually created and manually hooked to the {@link ResponsiveBot${symbol_pound}getWorldView()}
|
||||
* via {@link IWorldView${symbol_pound}addEventListener(Class, IWorldEventListener)}
|
||||
* method inside {@link ResponsiveBot${symbol_pound}prepareBot(UT2004Bot)}.
|
||||
*
|
||||
* <p><p>
|
||||
* Note, that this is old/manual way how to add listeners on various events that are rised
|
||||
* within the {@link IWorldView} (obtainable from {@link UT2004Bot${symbol_pound}getWorldView()} via
|
||||
* <code>bot.getWorldView()</code> or simply accessing {@link UT2004BotModuleController${symbol_pound}world} field).
|
||||
*
|
||||
* <p><p>
|
||||
* Such event listener MUST BE registered via some method of {@link IWorldView} offers.
|
||||
* This particular listener is registered inside {@link ResponsiveBot${symbol_pound}prepareBot(cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004Bot)}.
|
||||
* Note that you can add/remove any listener during runtime.
|
||||
*/
|
||||
IWorldEventListener<BotDamaged> botDamagedListener = new IWorldEventListener<BotDamaged>() {
|
||||
|
||||
@Override
|
||||
public void notify(BotDamaged event) {
|
||||
// the bot was injured - let's move around the level and hope that we will find a health pack
|
||||
// note that we have to acquire "SECOND" nearest navpoint, as the first one is the navpoint we're standing at
|
||||
NavPoint secondNav = DistanceUtils.getSecondNearest(getWorldView().getAll(NavPoint.class).values(), info.getLocation());
|
||||
// always check even for improbable conditions
|
||||
if (secondNav == null) {
|
||||
// try to locate some navpoint
|
||||
move.turnVertical(30);
|
||||
} else {
|
||||
// move to it
|
||||
move.moveTo(secondNav);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Example usage of {@link ObjectListener} that will listen on every change
|
||||
* / event that will be raised on the concrete {@link IWorldObject}, in this
|
||||
* case on the {@link GameInfo}.
|
||||
*
|
||||
* <p><p>
|
||||
* Notice that we have to specify which ID
|
||||
* class the world object is using and have explicit representation of it's
|
||||
* id - note that this is totally unsuitable for any dynamic IDs, such as
|
||||
* NavPoint ids, etc... you will probably never use this annotation.
|
||||
*
|
||||
* <p><p>
|
||||
* See implementations of {@link IWorldObjectEvent}, which are
|
||||
* {@link WorldObjectFirstEncounteredEvent}, {@link WorldObjectAppearedEvent},
|
||||
* {@link WorldObjectUpdatedEvent}, {@link WorldObjectDisappearedEvent}
|
||||
* and {@link WorldObjectDestroyedEvent}. All such events may be possibly
|
||||
* caught by this {@link ObjectListener} annotated method.
|
||||
*
|
||||
* @param info
|
||||
*/
|
||||
@ObjectListener(idClass = UnrealId.class, objectId = "GameInfoId")
|
||||
public void gameInfo1(IWorldObjectEvent<GameInfo> gameInfoEvent) {
|
||||
log.warning("GAME INFO EVENT =1=: " + gameInfoEvent);
|
||||
}
|
||||
|
||||
/**
|
||||
* Example usage of {@link ObjectEventListener} that will listen on SPECIFIC
|
||||
* event that is raised on the concrete {@link IWorldObject}. As is the case
|
||||
* of {@link ResponsiveBot${symbol_pound}gameInfo1(IWorldObjectEvent)}, you will probably
|
||||
* never use this.
|
||||
*
|
||||
* @param gameInfoEvent
|
||||
*/
|
||||
@ObjectEventListener(idClass = UnrealId.class, objectId = "GameInfoId", eventClass = WorldObjectUpdatedEvent.class)
|
||||
public void gameInfo2(WorldObjectUpdatedEvent<GameInfo> gameInfoEvent) {
|
||||
log.warning("GAME INFO EVENT =2=: " + gameInfoEvent);
|
||||
}
|
||||
|
||||
/**
|
||||
* Example usage of {@link ObjectClassListener} notice the difference
|
||||
* between this listener and {@link ObjectClassEventListener} that is used
|
||||
* on {@link ResponsiveBot${symbol_pound}playerAppeared(WorldObjectAppearedEvent)}.
|
||||
*
|
||||
* <p><p>
|
||||
* This method will receive ALL events that are raised on any {@link Player}
|
||||
* object whereas {@link ResponsiveBot${symbol_pound}playerAppeared(WorldObjectAppearedEvent)}
|
||||
* will receive only {@link WorldObjectAppearedEvent}.
|
||||
*
|
||||
* <p><p>
|
||||
* See implementations of {@link IWorldObjectEvent}, which are
|
||||
* {@link WorldObjectFirstEncounteredEvent}, {@link WorldObjectAppearedEvent},
|
||||
* {@link WorldObjectUpdatedEvent}, {@link WorldObjectDisappearedEvent}
|
||||
* and {@link WorldObjectDestroyedEvent}. All such events may be possibly
|
||||
* caught by this {@link ObjectListener} annotated method.
|
||||
*
|
||||
* @param playerEvent
|
||||
*/
|
||||
@ObjectClassListener(objectClass = Player.class)
|
||||
public void playerEvent(IWorldObjectEvent<Player> playerEvent) {
|
||||
log.warning("PLAYER EVENT: " + playerEvent);
|
||||
}
|
||||
|
||||
/**
|
||||
* If you uncomment {@link EventListener} annotation below this comment, this message
|
||||
* will be triggered every time the GB2004 sends EndMessage to you. It will (more-less)
|
||||
* act the same way as {@link ResponsiveBot${symbol_pound}logic()} method.
|
||||
* @param event
|
||||
*/
|
||||
//@EventListener(eventClass=EndMessage.class)
|
||||
public void gb2004BatchEnd(EndMessage event) {
|
||||
log.info("EndMessage received!");
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialize all necessary variables here, before the bot actually receives
|
||||
* anything from the environment + hook up your custom listener.
|
||||
*/
|
||||
@Override
|
||||
public void prepareBot(UT2004Bot bot) {
|
||||
// register the botDamagedListener that we have previously created
|
||||
getWorldView().addEventListener(BotDamaged.class, botDamagedListener);
|
||||
}
|
||||
|
||||
/**
|
||||
* Here we can modify initialize command for our bot if we want to.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Initialize getInitializeCommand() {
|
||||
return new Initialize();
|
||||
}
|
||||
|
||||
/**
|
||||
* The bot is initialized in the environment - a physical representation of
|
||||
* the bot is present in the game.
|
||||
*
|
||||
* @param config information about configuration
|
||||
* @param init information about configuration
|
||||
*/
|
||||
@Override
|
||||
public void botFirstSpawn(GameInfo gameInfo, ConfigChange config, InitedMessage init, Self self) {
|
||||
// notify the world (i.e., send message to UT2004) that the bot is up and running
|
||||
body.getCommunication().sendGlobalTextMessage("I am alive!");
|
||||
}
|
||||
|
||||
/**
|
||||
* This method is called only once right before actual logic() method is
|
||||
* called for the first time. Similar to {@link ResponsiveBot${symbol_pound}botFirstSpawn(cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo, cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ConfigChange, cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.InitedMessage, cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Self)}.
|
||||
*/
|
||||
@Override
|
||||
public void beforeFirstLogic() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Main method that controls the bot - makes decisions what to do next.
|
||||
* <p><p> Notice that the method is empty as this bot is completely
|
||||
* event-driven.
|
||||
*/
|
||||
@Override
|
||||
public void logic() throws PogamutException {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called each time our bot die. Good for reseting all bot state dependent
|
||||
* variables.
|
||||
*
|
||||
* @param event
|
||||
*/
|
||||
@Override
|
||||
public void botKilled(BotKilled event) {
|
||||
}
|
||||
|
||||
/**
|
||||
* This method is called when the bot is started either from IDE or from
|
||||
* command line.
|
||||
*
|
||||
* @param args
|
||||
*/
|
||||
public static void main(String args[]) throws PogamutException {
|
||||
// wrapped logic for bots executions, suitable to run single bot in single JVM
|
||||
new UT2004BotRunner(ResponsiveBot.class, "ResponsiveBot").setMain(true).startAgent();
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user