View Javadoc

1   package cz.cuni.amis.pogamut.ut2004.analyzer;
2   
3   import java.io.File;
4   import java.io.PrintWriter;
5   
6   import com.google.inject.Inject;
7   
8   import cz.cuni.amis.pogamut.base.communication.command.IAct;
9   import cz.cuni.amis.pogamut.base.communication.worldview.event.IWorldEventListener;
10  import cz.cuni.amis.pogamut.base.communication.worldview.object.IWorldObjectEventListener;
11  import cz.cuni.amis.pogamut.base.communication.worldview.object.event.WorldObjectUpdatedEvent;
12  import cz.cuni.amis.pogamut.base.component.bus.IComponentBus;
13  import cz.cuni.amis.pogamut.base.utils.logging.IAgentLogger;
14  import cz.cuni.amis.pogamut.base.utils.math.DistanceUtils;
15  import cz.cuni.amis.pogamut.unreal.communication.messages.UnrealId;
16  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.ConfigurationObserver;
17  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbcommands.InitializeObserver;
18  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.AddInventoryMsg;
19  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.AdrenalineGained;
20  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.BotKilled;
21  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Bumped;
22  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ChangedWeapon;
23  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ComboStarted;
24  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.FallEdge;
25  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameInfo;
26  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GameRestarted;
27  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.GlobalChat;
28  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.HearNoise;
29  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.HearPickup;
30  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.IncomingProjectile;
31  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ItemPickedUp;
32  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.JumpPerformed;
33  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Landed;
34  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.LostChild;
35  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.MyInventory;
36  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Player;
37  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerDamaged;
38  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerJoinsGame;
39  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerKilled;
40  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerLeft;
41  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.PlayerScore;
42  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.RecordingEnded;
43  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.RecordingStarted;
44  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Self;
45  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ShootingStarted;
46  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.ShootingStopped;
47  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Spawn;
48  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.Thrown;
49  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.WallCollision;
50  import cz.cuni.amis.pogamut.ut2004.communication.messages.gbinfomessages.WeaponUpdate;
51  import cz.cuni.amis.pogamut.ut2004.communication.worldview.UT2004WorldView;
52  import cz.cuni.amis.pogamut.ut2004.observer.impl.UT2004Observer;
53  import cz.cuni.amis.utils.exception.PogamutException;
54  
55  /**
56   * Similar to {@link UT2004AnalyzerObserver}, but it may output ALL MESSAGES for a given bot.
57   * 
58   * @author Jimmy
59   */
60  public class UT2004AnalyzerFullObserver extends UT2004Observer implements IUT2004AnalyzerObserver {
61  	
62  	private UnrealId observedBotId;	
63  	
64  	private IWorldEventListener<GameRestarted> gameRestartedListener = new IWorldEventListener<GameRestarted>() {
65  
66  		@Override
67  		public void notify(GameRestarted event) {
68  			if (event.isStarted()) {
69  				gameRestartStarted();
70  			} else 
71  			if (event.isFinished()) {
72  				gameRestartEnd();
73  			} else {
74  				throw new PogamutException("GameRestarted has started==false && finished==false as well, invalid!", this);
75  			}
76  		}
77  		
78  	};
79  	
80  	@Inject
81  	public UT2004AnalyzerFullObserver(UT2004AnalyzerFullObserverParameters params,
82  			IComponentBus bus, IAgentLogger agentLogger,
83  			UT2004WorldView worldView, IAct act) {
84  		super(params, bus, agentLogger, worldView, act);
85  		observedBotId = UnrealId.get(params.getObservedAgentId());
86  		getWorldView().addEventListener(GameRestarted.class, gameRestartedListener);
87  		getWorldView().addObjectListener(Self.class, WorldObjectUpdatedEvent.class, humanLike_selfListener);
88  		if (params.isHumanLikeObservingEnabled()) {
89  			initializeHumanLikeObserving(params.getHumanLikeBotName(), params.getHumanLikeWriter());
90  		}
91  	}
92  	
93  	@Override
94  	public UT2004AnalyzerFullObserverParameters getParams() {
95  		return (UT2004AnalyzerFullObserverParameters) super.getParams();
96  	}
97  
98  	@Override
99  	public UnrealId getObservedBotId() {
100 		return observedBotId;
101 	}
102 	
103 	/**
104 	 * Returns path to file that should be used for outputting the data
105 	 * @return
106 	 */
107 	public String getOutputFilePath() {
108 		String path = getParams().getOutputPath();
109 		if (path == null) path = ".";
110 		path += File.separator;
111 		if (getParams().getFileName() != null) {
112 			path += getParams().getFileName();
113 		} else {
114 			path += getObservedBotId().getStringId();
115 			path += ".csv";
116 		}
117 		return path;
118 	}
119 	
120 	/**
121 	 * Called whenever {@link GameRestart} message with {@link GameRestarted#isStarted()} is received.
122 	 * <p><p>
123 	 * You probably won't need to override this method, better override {@link UT2004AnalyzerFullObserver#gameRestartEnd()}, that
124 	 * is the place where you should reset data collection statistics / start them in case of {@link UT2004AnalyzerObserverParameters#isWaitForMatchRestart()}.
125 	 * <p><p>
126 	 * Current implementation is empty.
127 	 */
128 	protected void gameRestartStarted() {
129 	}
130 	
131 	/**
132 	 * Called whenever {@link GameRestart} message with {@link GameRestarted#isFinished()} is received.
133 	 * <p><p>
134 	 * Place where you should reset data collection statistics / start them 
135 	 * in case of {@link UT2004AnalyzerObserverParameters#isWaitForMatchRestart()}.
136 	 * <p><p>
137 	 * Current implementation is empty.
138 	 */
139 	protected void gameRestartEnd() {
140 	}
141 	
142 	/**
143 	 * Initialize the observer to listen on the {@link UT2004AnalyzerObserverParameters#getObservedAgentId()} that is obtained from
144 	 * the {@link UT2004AnalyzerFullObserver#getParams()}.
145 	 */
146 	@Override
147 	protected void startAgent() {
148 		super.startAgent();
149 		getAct().act(new InitializeObserver().setId(getParams().getObservedAgentId()));
150 		configureObserver();
151 	}
152 	
153 	@Override
154 	protected void startPausedAgent() {
155 		super.startPausedAgent();
156 		getAct().act(new InitializeObserver().setId(getParams().getObservedAgentId()));
157 		configureObserver();
158 	}
159 	
160 	/**
161 	 * Called from the {@link UT2004AnalyzerFullObserver#startAgent()} after {@link InitializeObserver} command
162 	 * is sent to configure the observer instance.
163 	 * <p><p>
164 	 * Actually enables {@link Self}, {@link MyInventory} and async messages (i.e., {@link BotKilled}).
165 	 */
166 	protected void configureObserver() {
167 		if (getParams().isHumanLikeObservingEnabled()) {
168 			getAct().act(new ConfigurationObserver().setUpdate(0.2).setAll(true).setSelf(true).setAsync(true).setGame(true).setSee(false).setSpecial(false));
169 		} else {
170 			getAct().act(new ConfigurationObserver().setUpdate(0.2).setAll(true).setSelf(true).setAsync(true).setGame(false).setSee(false).setSpecial(false));
171 		}
172 	}
173 	
174 	//
175 	// HUMAN-LIKE OBSERVING
176 	//
177 	
178 	/**
179      * Enemy of the particular observed player.
180      */
181     private Player humanLike_enemy = null;
182     /**
183      * Name of the particular observed player.
184      */
185     private String humanLike_playerName;
186     /**
187      * Where we should output humanLike log.
188      */
189     private PrintWriter humanLike_writer; 
190     /**
191      * Delimiter separating parts of saved log messages. Parts are player name,
192      * time, type of message and a GameBots message.
193      */
194     public static final String humanLike_DELIMITER = "$";
195     
196     /**
197      * Add inventory message.
198      */
199     IWorldEventListener<AddInventoryMsg> humanLike_addInventoryMsgListener = new IWorldEventListener<AddInventoryMsg>() {
200         @Override
201         public void notify(AddInventoryMsg event) {
202             processAddInventoryMsgEvent(event);
203         }
204     };
205     /**
206      * Adrenaline gained.
207      */
208     IWorldEventListener<AdrenalineGained> humanLike_adrenalineGainedListener = new IWorldEventListener<AdrenalineGained>() {
209         @Override
210         public void notify(AdrenalineGained event) {
211             processAdrenalineGainedEvent(event);
212         }
213     };
214     /**
215      * Bumped.
216      */
217     IWorldEventListener<Bumped> humanLike_bumpedListener = new IWorldEventListener<Bumped>() {
218         @Override
219         public void notify(Bumped event) {
220             processBumpedEvent(event);
221         }
222     };
223     /**
224      * Changed weapon.
225      */
226     IWorldEventListener<ChangedWeapon> humanLike_changedWeaponListener = new IWorldEventListener<ChangedWeapon>() {
227         @Override
228         public void notify(ChangedWeapon event) {
229             processChangedWeaponEvent(event);
230         }
231     };
232     /**
233      * Combo started.
234      */
235     IWorldEventListener<ComboStarted> humanLike_comboStartedListener = new IWorldEventListener<ComboStarted>() {
236         @Override
237         public void notify(ComboStarted event) {
238             processComboStartedEvent(event);
239         }
240     };
241     /**
242      * Fall edge.
243      */
244     IWorldEventListener<FallEdge> humanLike_fallEdgeListener = new IWorldEventListener<FallEdge>() {
245         @Override
246         public void notify(FallEdge event) {
247             processFallEdgeEvent(event);
248         }
249     };
250     /**
251      * Game info.
252      */
253     IWorldEventListener<GameInfo> humanLike_gameInfoListener = new IWorldEventListener<GameInfo>() {
254         @Override
255         public void notify(GameInfo event) {
256             processGameInfoEvent(event);
257         }
258     };
259     /**
260      * Global chat.
261      */
262     IWorldEventListener<GlobalChat> humanLike_globalChatListener = new IWorldEventListener<GlobalChat>() {
263         @Override
264         public void notify(GlobalChat event) {
265             processGlobalChatEvent(event);
266         }
267     };
268     /**
269      * Hear noise.
270      */
271     IWorldEventListener<HearNoise> humanLike_hearNoiseListener = new IWorldEventListener<HearNoise>() {
272         @Override
273         public void notify(HearNoise event) {
274             processHearNoiseEvent(event);
275         }
276     };
277     /**
278      * Hear pickup.
279      */
280     IWorldEventListener<HearPickup> humanLike_hearPickupListener = new IWorldEventListener<HearPickup>() {
281         @Override
282         public void notify(HearPickup event) {
283             processHearPickupEvent(event);
284         }
285     };
286     /**
287      * Incoming projectile.
288      */
289     IWorldEventListener<IncomingProjectile> humanLike_incomingProjectileListener = new IWorldEventListener<IncomingProjectile>() {
290         @Override
291         public void notify(IncomingProjectile event) {
292             processIncomingProjectileEvent(event);
293         }
294     };
295     /**
296      * Item picked up.
297      */
298     IWorldEventListener<ItemPickedUp> humanLike_itemPickedUpListener = new IWorldEventListener<ItemPickedUp>() {
299         @Override
300         public void notify(ItemPickedUp event) {
301             processItemPickedUpEvent(event);
302         }
303     };
304     /**
305      * Jump performed.
306      */
307     IWorldEventListener<JumpPerformed> humanLike_jumpPerformedListener = new IWorldEventListener<JumpPerformed>() {
308         @Override
309         public void notify(JumpPerformed event) {
310             processJumpPerformedEvent(event);
311         }
312     };
313     /**
314      * Landed.
315      */
316     IWorldEventListener<Landed> humanLike_landedListener = new IWorldEventListener<Landed>() {
317         @Override
318         public void notify(Landed event) {
319             processLandedEvent(event);
320         }
321     };
322     /**
323      * Lost child.
324      */
325     IWorldEventListener<LostChild> humanLike_lostChildListener = new IWorldEventListener<LostChild>() {
326         @Override
327         public void notify(LostChild event) {
328             processLostChildEvent(event);
329         }
330     };
331     /**
332      * Player damaged.
333      */
334     IWorldEventListener<PlayerDamaged> humanLike_playerDamagedListener = new IWorldEventListener<PlayerDamaged>() {
335         @Override
336         public void notify(PlayerDamaged event) {
337             processPlayerDamagedEvent(event);
338         }
339     };
340     /**
341      * Player joins game.
342      */
343     IWorldEventListener<PlayerJoinsGame> humanLike_playerJoinsGameListener = new IWorldEventListener<PlayerJoinsGame>() {
344         @Override
345         public void notify(PlayerJoinsGame event) {
346             processPlayerJoinsGameEvent(event);
347         }
348     };
349     /**
350      * Player killed.
351      */
352     IWorldEventListener<PlayerKilled> humanLike_playerKilledListener = new IWorldEventListener<PlayerKilled>() {
353         @Override
354         public void notify(PlayerKilled event) {
355             processPlayerKilledEvent(event);
356         }
357     };
358     /**
359      * Player left.
360      */
361     IWorldEventListener<PlayerLeft> humanLike_playerLeftListener = new IWorldEventListener<PlayerLeft>() {
362         @Override
363         public void notify(PlayerLeft event) {
364             processPlayerLeftEvent(event);
365         }
366     };
367     /**
368      * Player score.
369      */
370     IWorldEventListener<PlayerScore> humanLike_playerScoreListener = new IWorldEventListener<PlayerScore>() {
371         @Override
372         public void notify(PlayerScore event) {
373             processPlayerScoreEvent(event);
374         }
375     };
376     /**
377      * Recording ended.
378      */
379     IWorldEventListener<RecordingEnded> humanLike_recordingEndedListener = new IWorldEventListener<RecordingEnded>() {
380         @Override
381         public void notify(RecordingEnded event) {
382             processRecordingEndedEvent(event);
383         }
384     };
385     /**
386      * Player score.
387      */
388     IWorldEventListener<RecordingStarted> humanLike_recordingStartedListener = new IWorldEventListener<RecordingStarted>() {
389         @Override
390         public void notify(RecordingStarted event) {
391             processRecordingStartedEvent(event);
392         }
393     };
394     /**
395      * Self.
396      */
397     IWorldObjectEventListener<Self, WorldObjectUpdatedEvent<Self>> humanLike_selfListener = new IWorldObjectEventListener<Self, WorldObjectUpdatedEvent<Self>>() {
398         @Override
399         public void notify(WorldObjectUpdatedEvent<Self> event) {
400             processSelfEvent(event);
401         }
402     };
403     /**
404      * Shooting started.
405      */
406     IWorldEventListener<ShootingStarted> humanLike_shootingStartedListener = new IWorldEventListener<ShootingStarted>() {
407         @Override
408         public void notify(ShootingStarted event) {
409             processShootingStartedEvent(event);
410         }
411     };
412     /**
413      * Shooting stopped.
414      */
415     IWorldEventListener<ShootingStopped> humanLike_shootingStoppedListener = new IWorldEventListener<ShootingStopped>() {
416         @Override
417         public void notify(ShootingStopped event) {
418             processShootingStoppedEvent(event);
419         }
420     };
421     /**
422      * Spawn.
423      */
424     IWorldEventListener<Spawn> humanLike_spawnListener = new IWorldEventListener<Spawn>() {
425         @Override
426         public void notify(Spawn event) {
427             processSpawnEvent(event);
428         }
429     };
430     /**
431      * Thrown.
432      */
433     IWorldEventListener<Thrown> humanLike_thrownListener = new IWorldEventListener<Thrown>() {
434         @Override
435         public void notify(Thrown event) {
436             processThrownEvent(event);
437         }
438     };
439     /**
440      * Wall collision.
441      */
442     IWorldEventListener<WallCollision> humanLike_wallCollisionListener = new IWorldEventListener<WallCollision>() {
443         @Override
444         public void notify(WallCollision event) {
445             processWallCollisionEvent(event);
446         }
447     };
448     /**
449      * Weapon update.
450      */
451     IWorldEventListener<WeaponUpdate> humanLike_weaponUpdateListener = new IWorldEventListener<WeaponUpdate>() {
452         @Override
453         public void notify(WeaponUpdate event) {
454             processWeaponUpdateEvent(event);
455         }
456     };
457 
458 	protected void save(String name, Long time, String type, String message) {
459         String output = name + humanLike_DELIMITER + time.toString() + humanLike_DELIMITER + type + humanLike_DELIMITER + message + "\n";
460         synchronized(humanLike_writer) {
461         	humanLike_writer.print(output);
462         }
463     }
464 
465     /**
466      * Process add inventory message event.
467      *
468      * @param event inventory message event
469      */
470     private void processAddInventoryMsgEvent(AddInventoryMsg event) {
471         save(humanLike_playerName, event.getSimTime(), "AddInventoryMsg", event.toString());
472     }
473 
474     /**
475      * Process adrenaline gained event.
476      *
477      * @param event adrenaline gained event
478      */
479     private void processAdrenalineGainedEvent(AdrenalineGained event) {
480         save(humanLike_playerName, event.getSimTime(), "AdrenalineGained", event.toString());
481     }
482 
483     /**
484      * Process bumped event.
485      *
486      * @param event bumped event
487      */
488     private void processBumpedEvent(Bumped event) {
489         save(humanLike_playerName, event.getSimTime(), "Bumped", event.toString());
490     }
491 
492     /**
493      * Process changed weapon event.
494      *
495      * @param event changed weapon event
496      */
497     private void processChangedWeaponEvent(ChangedWeapon event) {
498         save(humanLike_playerName, event.getSimTime(), "ChangedWeapon", event.toString());
499     }
500 
501     /**
502      * Process combo started event.
503      *
504      * @param event combo started event
505      */
506     private void processComboStartedEvent(ComboStarted event) {
507         save(humanLike_playerName, event.getSimTime(), "ComboStarted", event.toString());
508     }
509 
510     /**
511      * Process fall edge event.
512      *
513      * @param event fall edge event
514      */
515     private void processFallEdgeEvent(FallEdge event) {
516         save(humanLike_playerName, event.getSimTime(), "FallEdge", event.toString());
517     }
518 
519     /**
520      * Process game info event.
521      *
522      * @param event game info event
523      */
524     private void processGameInfoEvent(GameInfo event) {
525         save(humanLike_playerName, event.getSimTime(), "GameInfo", event.toString());
526     }
527 
528     /**
529      * Process global chat event.
530      *
531      * @param event global chat event
532      */
533     private void processGlobalChatEvent(GlobalChat event) {
534         save(humanLike_playerName, event.getSimTime(), "GlobalChat", event.toString());
535     }
536 
537     /**
538      * Process hear noise event.
539      *
540      * @param event hear noise event
541      */
542     private void processHearNoiseEvent(HearNoise event) {
543         save(humanLike_playerName, event.getSimTime(), "HearNoise", event.toString());
544     }
545 
546     /**
547      * Process hear pickup event.
548      *
549      * @param event hear pickup event
550      */
551     private void processHearPickupEvent(HearPickup event) {
552         save(humanLike_playerName, event.getSimTime(), "HearPickup", event.toString());
553     }
554 
555     /**
556      * Process incoming projectile event.
557      *
558      * @param event incoming projectile event
559      */
560     private void processIncomingProjectileEvent(IncomingProjectile event) {
561         save(humanLike_playerName, event.getSimTime(), "IncomingProjectile", event.toString());
562     }
563 
564     /**
565      * Process item picked up event.
566      *
567      * @param event item picked up event
568      */
569     private void processItemPickedUpEvent(ItemPickedUp event) {
570         save(humanLike_playerName, event.getSimTime(), "ItemPickedUp", event.toString());
571     }
572 
573     /**
574      * Process jump performed event.
575      *
576      * @param event jump performed event
577      */
578     private void processJumpPerformedEvent(JumpPerformed event) {
579         save(humanLike_playerName, event.getSimTime(), "JumpPerformed", event.toString());
580     }
581 
582     /**
583      * Process landed event.
584      *
585      * @param event landed event
586      */
587     private void processLandedEvent(Landed event) {
588         save(humanLike_playerName, event.getSimTime(), "Landed", event.toString());
589     }
590 
591     /**
592      * Process lost child event.
593      *
594      * @param event lost child event
595      */
596     private void processLostChildEvent(LostChild event) {
597         save(humanLike_playerName, event.getSimTime(), "LostChild", event.toString());
598     }
599 
600     /**
601      * Process player damaged event.
602      *
603      * @param event player damaged event
604      */
605     private void processPlayerDamagedEvent(PlayerDamaged event) {
606         save(humanLike_playerName, event.getSimTime(), "PlayerDamaged", event.toString());
607     }
608 
609     /**
610      * Process player joins game event.
611      *
612      * @param event player joins game event
613      */
614     private void processPlayerJoinsGameEvent(PlayerJoinsGame event) {
615         save(humanLike_playerName, event.getSimTime(), "PlayerJoinsGame", event.toString());
616     }
617 
618     /**
619      * Process player killed event.
620      *
621      * @param event player killed event
622      */
623     private void processPlayerKilledEvent(PlayerKilled event) {
624         save(humanLike_playerName, event.getSimTime(), "PlayerKilled", event.toString());
625     }
626 
627     /**
628      * Process player left event.
629      *
630      * @param event player left event
631      */
632     private void processPlayerLeftEvent(PlayerLeft event) {
633         save(humanLike_playerName, event.getSimTime(), "PlayerLeft", event.toString());
634     }
635 
636     /**
637      * Process player score event.
638      *
639      * @param event player score event
640      */
641     private void processPlayerScoreEvent(PlayerScore event) {
642         save(humanLike_playerName, event.getSimTime(), "PlayerScore", event.toString());
643     }
644 
645     /**
646      * Process recording ended event.
647      *
648      * @param event recording ended event
649      */
650     private void processRecordingEndedEvent(RecordingEnded event) {
651         save(humanLike_playerName, event.getSimTime(), "RecordingEnded", event.toString());
652     }
653 
654     /**
655      * Process recording started event.
656      *
657      * @param event recording started event
658      */
659     private void processRecordingStartedEvent(RecordingStarted event) {
660         save(humanLike_playerName, event.getSimTime(), "RecordingStarted", event.toString());
661     }
662 
663     /**
664      * READ-ONLY, {@link Self} object of the observed bot.
665      */
666 	private Self botSelf;
667 	
668 	/**
669      * READ-ONLY, {@link Self} object of the observed bot.
670      */
671     public Self getBotSelf() {
672 		return botSelf;
673 	}
674     
675     /**
676      * Process self event.
677      *
678      * @param event self event
679      */
680     private void processSelfEvent(WorldObjectUpdatedEvent<Self> event) {
681     	this.botSelf = event.getObject();
682     	if (getParams().isHumanLikeObservingEnabled()) {
683     		save(humanLike_playerName, event.getObject().getSimTime(), "Self", event.getObject().toString());
684     		processEnemyEvent(event);
685     	}
686     }
687 
688     /**
689      * Process shooting started event.
690      *
691      * @param event shooting started event
692      */
693     private void processShootingStartedEvent(ShootingStarted event) {
694         save(humanLike_playerName, event.getSimTime(), "ShootingStarted", event.toString());
695     }
696 
697     /**
698      * Process shooting stopped event.
699      *
700      * @param event shooting stopped event
701      */
702     private void processShootingStoppedEvent(ShootingStopped event) {
703         save(humanLike_playerName, event.getSimTime(), "ShootingStopped", event.toString());
704     }
705 
706     /**
707      * Process spawn event.
708      *
709      * @param event spawn event
710      */
711     private void processSpawnEvent(Spawn event) {
712         save(humanLike_playerName, event.getSimTime(), "Spawn", event.toString());
713     }
714 
715     /**
716      * Process thrown event.
717      *
718      * @param event thrown event
719      */
720     private void processThrownEvent(Thrown event) {
721         save(humanLike_playerName, event.getSimTime(), "Thrown", event.toString());
722     }
723 
724     /**
725      * Process wall collision event.
726      *
727      * @param event wall collision event
728      */
729     private void processWallCollisionEvent(WallCollision event) {
730         save(humanLike_playerName, event.getSimTime(), "WallCollision", event.toString());
731     }
732 
733     /**
734      * Process weapon update event.
735      *
736      * @param event weapon update event
737      */
738     private void processWeaponUpdateEvent(WeaponUpdate event) {
739         save(humanLike_playerName, event.getSimTime(), "WeaponUpdate", event.toString());
740     }
741 
742     /**
743      * Process enemy event.
744      *
745      * @param event enemy event
746      */
747     private void processEnemyEvent(WorldObjectUpdatedEvent<Self> event) {
748         locateEnemy(event);
749         if (humanLike_enemy != null) {
750             save(humanLike_playerName, event.getObject().getSimTime(), "Enemy", humanLike_enemy.toString());
751         }
752     }
753 
754     /**
755      * Locate player's enemy. Save reference on player's enemy. If there is no
756      * new enemy, it will keep the last one in memory.
757      *
758      * @param event enemy update
759      */
760     private void locateEnemy(WorldObjectUpdatedEvent<Self> event) {
761         humanLike_enemy = DistanceUtils.getNearestVisible(getWorldView().getAllVisible(Player.class).values(), event.getObject().getLocation());
762         if (humanLike_enemy != null && humanLike_enemy.getName().toString().equals(humanLike_playerName)) {
763             humanLike_enemy = null;
764         }
765     }
766 
767     /**
768      * Initialize listeners. We call this method manually - we register
769      * listeners here.
770      *
771      * @param observedPlayer name of observed player
772      * @param printWriter 
773      */
774     protected void initializeHumanLikeObserving(String observedPlayer, PrintWriter printWriter) {
775 
776     	// init writer
777     	humanLike_writer = printWriter;
778     	if (humanLike_writer == null) {
779     		throw new RuntimeException("humanLike_writer is null! Invalid observer parameters passed...");
780     	}
781     	
782         // initialize listeners
783         getWorldView().addEventListener(AddInventoryMsg.class, humanLike_addInventoryMsgListener);
784         getWorldView().addEventListener(AdrenalineGained.class, humanLike_adrenalineGainedListener);
785         getWorldView().addEventListener(Bumped.class, humanLike_bumpedListener);
786         getWorldView().addEventListener(ChangedWeapon.class, humanLike_changedWeaponListener);
787         getWorldView().addEventListener(ComboStarted.class, humanLike_comboStartedListener);
788         getWorldView().addEventListener(FallEdge.class, humanLike_fallEdgeListener);
789         getWorldView().addEventListener(GameInfo.class, humanLike_gameInfoListener);
790         getWorldView().addEventListener(GlobalChat.class, humanLike_globalChatListener);
791         getWorldView().addEventListener(HearNoise.class, humanLike_hearNoiseListener);
792         getWorldView().addEventListener(HearPickup.class, humanLike_hearPickupListener);
793         getWorldView().addEventListener(IncomingProjectile.class, humanLike_incomingProjectileListener);
794         getWorldView().addEventListener(ItemPickedUp.class, humanLike_itemPickedUpListener);
795         getWorldView().addEventListener(JumpPerformed.class, humanLike_jumpPerformedListener);
796         getWorldView().addEventListener(Landed.class, humanLike_landedListener);
797         getWorldView().addEventListener(LostChild.class, humanLike_lostChildListener);
798         getWorldView().addEventListener(PlayerDamaged.class, humanLike_playerDamagedListener);
799         getWorldView().addEventListener(PlayerJoinsGame.class, humanLike_playerJoinsGameListener);
800         getWorldView().addEventListener(PlayerKilled.class, humanLike_playerKilledListener);
801         getWorldView().addEventListener(PlayerLeft.class, humanLike_playerLeftListener);
802         getWorldView().addEventListener(PlayerScore.class, humanLike_playerScoreListener);
803         getWorldView().addEventListener(RecordingEnded.class, humanLike_recordingEndedListener);
804         getWorldView().addEventListener(RecordingStarted.class, humanLike_recordingStartedListener);        
805         getWorldView().addEventListener(ShootingStarted.class, humanLike_shootingStartedListener);
806         getWorldView().addEventListener(ShootingStopped.class, humanLike_shootingStoppedListener);
807         getWorldView().addEventListener(Spawn.class, humanLike_spawnListener);
808         getWorldView().addEventListener(Thrown.class, humanLike_thrownListener);
809         getWorldView().addEventListener(WallCollision.class, humanLike_wallCollisionListener);
810         getWorldView().addEventListener(WeaponUpdate.class, humanLike_weaponUpdateListener);
811 
812         // save player name
813         humanLike_playerName = observedPlayer;
814     }
815 
816 }