View Javadoc

1   /*
2    * @(#)ProgressDataAndTime.java Jun 8, 2004
3    * 
4    * 
5    * Copyright (c) 2003-2005 Delft University of Technology, Jaffalaan 5, 2628 BX
6    * Delft, the Netherlands. All rights reserved.
7    * 
8    * See for project information <a href="http://www.simulation.tudelft.nl/">
9    * www.simulation.tudelft.nl </a>.
10   * 
11   * The source code and binary code of this software is proprietary information
12   * of Delft University of Technology.
13   */
14  
15  package org.gscg.common.interactionlayer.timecontrol;
16  
17  import java.io.IOException;
18  import java.io.ObjectOutputStream;
19  import java.io.Serializable;
20  import java.rmi.RemoteException;
21  import java.text.DateFormat;
22  import java.util.Calendar;
23  
24  import nl.tudelft.simulation.dsol.experiment.TimeUnit;
25  import nl.tudelft.simulation.dsol.experiment.TimeUnitInterface;
26  import nl.tudelft.simulation.dsol.simulators.SimulatorInterface;
27  import nl.tudelft.simulation.event.Event;
28  import nl.tudelft.simulation.event.EventInterface;
29  import nl.tudelft.simulation.event.EventListenerInterface;
30  import nl.tudelft.simulation.event.EventProducer;
31  import nl.tudelft.simulation.logger.Logger;
32  
33  import org.gscg.common.interactionlayer.dataobjects.ProgressionData;
34  
35  /***
36   * The GlobalProgressDataAndTime object manages progress time for all the
37   * objects part of an interactive distributed simulation. Implementing progress
38   * control in this way makes sure that not every actor in a game is going to
39   * perform this expensive code every time for itself, instead we use a 'global'
40   * approach, and thus increase our performance.
41   * 
42   * Copyright (c) 2003-2005 Delft University of Technology, Jaffalaan 5, 2628 BX
43   * Delft, the Netherlands. All rights reserved.
44   * 
45   * See for project information <a href="http://www.simulation.tudelft.nl/">
46   * www.simulation.tudelft.nl </a>.
47   * 
48   * The source code and binary code of this software is proprietary information
49   * of Delft University of Technology.
50   * 
51   * @author <a
52   *         href="http://www.tbm.tudelft.nl/webstaf/stijnh/index.htm">Stijn-Pieter
53   *         van Houten </a>
54   * @version $Revision: 1.1 $ $Date: 2005/06/16 12:34:02 $
55   * @since 1.0.0
56   */
57  public class GlobalProgressDateAndTime implements Serializable
58  {
59  	/*** the serial version uid */
60  	private static final long serialVersionUID = 11L;
61  
62  	/*** the event producer */
63  	private CustomEventProducer customEventProducer = null;
64  
65  	/*** the static progress data and time instance */
66  	private static GlobalProgressDateAndTime staticProgressDateAndTime = null;
67  
68  	/*** the formatted date */
69  	private static String date;
70  
71  	/*** the progress */
72  	private static double progress = Double.NaN;
73  
74  	/*** indicates the progeress in the number of time units */
75  	private static String progressTime = "";
76  
77  	/*** the start time */
78  	private static long startTime = 0L;
79  
80  	/*** the stop time as a string */
81  	private static String stopTime;
82  
83  	/*** the formatted time */
84  	private static String time;
85  
86  	/*** the stop time */
87  	private static int intStopTime = 0;
88  
89  	/*** the value of the time unit */
90  	private static long unitValue = 0L;
91  
92  	/*** the time unit to use */
93  	private static TimeUnitInterface timeUnit = null;
94  
95  	/*** for efficiency */
96  	private static int lastHour = -1;
97  
98  	/*** calender object */
99  	private static Calendar calendar = Calendar.getInstance();
100 
101 	/*** the event listener */
102 	private CustomEventListener customEventListener = null;
103 
104 	/*** the simulator to use */
105 	private SimulatorInterface simulator = null;
106 
107 	/*** the start time */
108 	private long instanceStartTime = 0L;
109 
110 	/*** the stop time */
111 	private int instanceStopTime = 0;
112 
113 	/*** the unit value */
114 	private long instanceUnitValue = 0L;
115 
116 	/*** the time unit */
117 	private TimeUnitInterface instanceTimeUnit = null;
118 
119 	/***
120 	 * initializes the different fields
121 	 * 
122 	 * @param staticProgressDateAndTime the private object
123 	 * @param startTime the start time
124 	 * @param stopTime the stop time
125 	 * @param unitValue the unit value
126 	 * @param timeUnit the time unit
127 	 */
128 	private static void initialize(
129 			final GlobalProgressDateAndTime staticProgressDateAndTime,
130 			final long startTime, final int stopTime, final long unitValue,
131 			final TimeUnitInterface timeUnit)
132 	{
133 		GlobalProgressDateAndTime.staticProgressDateAndTime = staticProgressDateAndTime;
134 		GlobalProgressDateAndTime.startTime = startTime;
135 		GlobalProgressDateAndTime.intStopTime = stopTime;
136 		GlobalProgressDateAndTime.unitValue = unitValue;
137 		GlobalProgressDateAndTime.timeUnit = timeUnit;
138 
139 		// the stop time won't change
140 		GlobalProgressDateAndTime.stopTime = ""
141 				+ (int) TimeUnit.convert(GlobalProgressDateAndTime.intStopTime,
142 						GlobalProgressDateAndTime.timeUnit,
143 						TimeUnitInterface.HOUR);
144 	}
145 
146 	/***
147 	 * constructs a new SimulationDateTime
148 	 * 
149 	 * @param simulator the simulator
150 	 */
151 	public GlobalProgressDateAndTime(final SimulatorInterface simulator)
152 	{
153 		super();
154 		this.simulator = simulator;
155 		this.customEventListener = new CustomEventListener();
156 		this.customEventProducer = new CustomEventProducer();
157 
158 		try
159 		{
160 			this.instanceStartTime = simulator.getReplication().getRunControl()
161 					.getTreatment().getStartTime();
162 			this.instanceStopTime = (int) this.simulator.getReplication()
163 					.getRunControl().getRunLength();
164 			this.instanceUnitValue = this.simulator.getReplication()
165 					.getRunControl().getTreatment().getTimeUnit().getValue();
166 			this.instanceTimeUnit = this.simulator.getReplication()
167 					.getRunControl().getTreatment().getTimeUnit();
168 			GlobalProgressDateAndTime.initialize(this, this.instanceStartTime,
169 					this.instanceStopTime, this.instanceUnitValue,
170 					this.instanceTimeUnit);
171 
172 			this.simulator.addListener(this.customEventListener,
173 					SimulatorInterface.TIME_CHANGED_EVENT);
174 		} catch (Exception exception)
175 		{
176 			exception.printStackTrace();
177 			Logger.severe(this, "<init>", exception);
178 		}
179 	}
180 
181 	/***
182 	 * Method getTime.
183 	 * 
184 	 * @param event the time changed event
185 	 */
186 	private static void getTime(final EventInterface event)
187 	{
188 		try
189 		{
190 			double hours = TimeUnit.convert(((Double) event.getContent())
191 					.doubleValue(), GlobalProgressDateAndTime.timeUnit,
192 					TimeUnitInterface.HOUR);
193 
194 			// make sure we only see hours up to 24
195 			hours = hours % 24;
196 
197 			if (GlobalProgressDateAndTime.lastHour != (int) hours)
198 			{
199 				GlobalProgressDateAndTime.lastHour = (int) hours;
200 				GlobalProgressDateAndTime.progress = ((Double) event
201 						.getContent()).doubleValue()
202 						/ GlobalProgressDateAndTime.intStopTime;
203 				GlobalProgressDateAndTime.progressTime = ""
204 						+ (int) (TimeUnit.convert(
205 								GlobalProgressDateAndTime.progress,
206 								GlobalProgressDateAndTime.timeUnit,
207 								TimeUnitInterface.HOUR) * GlobalProgressDateAndTime.intStopTime);
208 
209 				int intHours = (int) Math.floor(hours);
210 				if (intHours < 10)
211 				{
212 					GlobalProgressDateAndTime.time = "0" + intHours + ":00";
213 
214 				} else
215 				{
216 					GlobalProgressDateAndTime.time = intHours + ":00";
217 				}
218 
219 				GlobalProgressDateAndTime.calendar
220 						.setTimeInMillis(GlobalProgressDateAndTime.startTime
221 								+ ((Double) event.getContent()).longValue()
222 								* GlobalProgressDateAndTime.unitValue);
223 				GlobalProgressDateAndTime.date = DateFormat.getDateInstance()
224 						.format(GlobalProgressDateAndTime.calendar.getTime());
225 
226 				// fill the data object
227 				ProgressionData data = new ProgressionData(
228 						GlobalProgressDateAndTime.date,
229 						GlobalProgressDateAndTime.time,
230 						GlobalProgressDateAndTime.stopTime,
231 						GlobalProgressDateAndTime.progress,
232 						GlobalProgressDateAndTime.progressTime);
233 
234 				// fire the event
235 				GlobalProgressDateAndTime.staticProgressDateAndTime.customEventProducer
236 						.fireEvent(new Event(
237 								SimulatorInterface.TIME_CHANGED_EVENT, null,
238 								data));
239 			}
240 		} catch (Exception exception)
241 		{
242 			Logger
243 					.severe(GlobalProgressDateAndTime.class, "getTime",
244 							exception);
245 		}
246 	}
247 
248 	/***
249 	 * Method getDate returns the date based on the simulator time.
250 	 * 
251 	 * @return returns a String reflecting the date of the simulation.
252 	 */
253 	public static String getDate()
254 	{
255 		String date = null;
256 		try
257 		{
258 			Calendar calendar = Calendar.getInstance();
259 			calendar
260 					.setTimeInMillis(GlobalProgressDateAndTime.startTime
261 							+ ((long) GlobalProgressDateAndTime.staticProgressDateAndTime.simulator
262 									.getSimulatorTime() * GlobalProgressDateAndTime.unitValue));
263 			date = DateFormat.getDateInstance().format(calendar.getTime());
264 		} catch (Exception exception)
265 		{
266 			Logger
267 					.severe(GlobalProgressDateAndTime.class, "getDate",
268 							exception);
269 		}
270 		return date;
271 	}
272 
273 	//
274 	// GETTERS
275 	//
276 	/***
277 	 * @return Returns the progress
278 	 */
279 	public static double getProgress()
280 	{
281 		return GlobalProgressDateAndTime.progress;
282 	}
283 
284 	/***
285 	 * @return Returns the progress time
286 	 */
287 	public static String getProgressTime()
288 	{
289 		return GlobalProgressDateAndTime.progressTime;
290 	}
291 
292 	/***
293 	 * @return Returns the stop time
294 	 */
295 	public static String getStopTime()
296 	{
297 		return GlobalProgressDateAndTime.stopTime;
298 	}
299 
300 	/***
301 	 * @return Returns the time
302 	 */
303 	public static String getTime()
304 	{
305 		return GlobalProgressDateAndTime.time;
306 	}
307 
308 	/***
309 	 * @return Returns the staticd progress and time instance
310 	 */
311 	public static GlobalProgressDateAndTime getStaticProgressDateAndTime()
312 	{
313 		return GlobalProgressDateAndTime.staticProgressDateAndTime;
314 	}
315 
316 	/***
317 	 * @return Returns the custom event producer
318 	 */
319 	public CustomEventProducer getCustomEventProducer()
320 	{
321 		return GlobalProgressDateAndTime.staticProgressDateAndTime.customEventProducer;
322 	}
323 
324 	//
325 	// private methods
326 	//
327 	/***
328 	 * writes a serializable method to stream
329 	 * 
330 	 * @param out the outputstream
331 	 * @throws IOException on IOException
332 	 */
333 	private synchronized void writeObject(final ObjectOutputStream out)
334 			throws IOException
335 	{
336 		out.defaultWriteObject();
337 		out.writeObject(GlobalProgressDateAndTime.date);
338 		out.writeObject(GlobalProgressDateAndTime.time);
339 		out.writeObject(GlobalProgressDateAndTime.stopTime);
340 		out.writeObject(new Double(GlobalProgressDateAndTime.progress));
341 		out.writeObject(GlobalProgressDateAndTime.progressTime);
342 	}
343 
344 	/***
345 	 * reads a serializable method from stream
346 	 * 
347 	 * @param in the inputstream
348 	 */
349 	private synchronized void readObject(final java.io.ObjectInputStream in)
350 	{
351 		try
352 		{
353 			in.defaultReadObject();
354 			// custome deserialize methods
355 			GlobalProgressDateAndTime.initialize(this, this.instanceStartTime,
356 					this.instanceStopTime, this.instanceUnitValue,
357 					this.instanceTimeUnit);
358 			GlobalProgressDateAndTime.date = (String) in.readObject();
359 			GlobalProgressDateAndTime.time = (String) in.readObject();
360 			GlobalProgressDateAndTime.stopTime = (String) in.readObject();
361 			GlobalProgressDateAndTime.progress = ((Double) in.readObject())
362 					.doubleValue();
363 			GlobalProgressDateAndTime.progressTime = (String) in.readObject();
364 
365 		} catch (Exception exception)
366 		{
367 			exception.printStackTrace();
368 		}
369 	}
370 
371 	/***
372 	 * A custom implementation of an event producer.
373 	 * <p>
374 	 * (c) copyright 2005 <a href="http://www.simulation.tudelft.nl">Delft
375 	 * University of Technology </a>, the Netherlands. <br>
376 	 * See for project information <a
377 	 * href="http://www.simulation.tudelft.nl">www.simulation.tudelft.nl </a>
378 	 * <br>
379 	 * 
380 	 * Copyright (c) 2003-2005 Delft University of Technology, Jaffalaan 5, 2628
381 	 * BX Delft, the Netherlands. All rights reserved.
382 	 * 
383 	 * See for project information <a href="http://www.simulation.tudelft.nl/">
384 	 * www.simulation.tudelft.nl </a>.
385 	 * 
386 	 * The source code and binary code of this software are proprietary
387 	 * information of Delft University of Technology.
388 	 * 
389 	 * @author <a
390 	 *         href="http://www.tbm.tudelft.nl/webstaf/stijnh/index.htm">Stijn-Pieter
391 	 *         van Houten </a>
392 	 * @version $Revision: 1.1 $ $Date: 2005/06/16 12:34:02 $
393 	 * @since 1.1.3
394 	 */
395 	public static class CustomEventProducer extends EventProducer implements
396 			Serializable
397 	{
398 		/*** the serial version uid */
399 		private static final long serialVersionUID = 11L;
400 
401 		/***
402 		 * constructs a new CustomEventProducer
403 		 */
404 		public CustomEventProducer()
405 		{
406 			super();
407 		}
408 
409 
410 		/***
411 		 * @see nl.tudelft.simulation.event.EventProducer#fireEvent(nl.tudelft.simulation.event.EventInterface)
412 		 */
413 		public synchronized EventInterface fireEvent(final EventInterface event)
414 		{
415 			return super.fireEvent(event);
416 		}
417 	}
418 
419 	/***
420 	 * A custom implementation of an event listener.
421 	 * <p>
422 	 * (c) copyright 2005 <a href="http://www.simulation.tudelft.nl">Delft
423 	 * University of Technology </a>, the Netherlands. <br>
424 	 * See for project information <a
425 	 * href="http://www.simulation.tudelft.nl">www.simulation.tudelft.nl </a>
426 	 * <br>
427 	 * 
428 	 * Copyright (c) 2003-2005 Delft University of Technology, Jaffalaan 5, 2628
429 	 * BX Delft, the Netherlands. All rights reserved.
430 	 * 
431 	 * See for project information <a href="http://www.simulation.tudelft.nl/">
432 	 * www.simulation.tudelft.nl </a>.
433 	 * 
434 	 * The source code and binary code of this software are proprietary
435 	 * information of Delft University of Technology.
436 	 * 
437 	 * @author <a
438 	 *         href="http://www.tbm.tudelft.nl/webstaf/stijnh/index.htm">Stijn-Pieter
439 	 *         van Houten </a>
440 	 * @version $Revision: 1.1 $ $Date: 2005/06/16 12:34:02 $
441 	 * @since 1.1.3
442 	 */
443 	private static class CustomEventListener implements EventListenerInterface,
444 			Serializable
445 	{
446 		/*** the serial version uid */
447 		private static final long serialVersionUID = 11L;
448 
449 		/***
450 		 * constructs a new CustomEventListener
451 		 */
452 		public CustomEventListener()
453 		{
454 			super();
455 		}
456 
457 		/***
458 		 * @see nl.tudelft.simulation.event.EventListenerInterface#notify(nl.tudelft.simulation.event.EventInterface)
459 		 */
460 		public void notify(final EventInterface event) throws RemoteException
461 		{
462 			if (event.getType().equals(SimulatorInterface.TIME_CHANGED_EVENT))
463 			{
464 				GlobalProgressDateAndTime.getTime(event);
465 			}
466 		}
467 	}
468 
469 }