001 package sale;
002
003 import sale.events.*;
004
005 import util.*;
006
007 /**
008 * This is a rather simple implementation of the {@link Timer Timer} interface.
009 *
010 * <p>It requires a Time object to work with. Every increasing of the timer has
011 * to be explicitly triggered by the {@link #goAhead goAhead()} method.</p>
012 *
013 * @author Stephan Gambke
014 * @version 2.0 11/06/1999
015 * @since v2.0
016 */
017 public class StepTimer extends Object implements Timer {
018
019 /**
020 * ID for serialization.
021 */
022 private static final long serialVersionUID = -5909676359937433717L;
023
024 /**
025 * The current Time.
026 *
027 * @serial
028 */
029 protected Time m_tTime;
030
031 /**
032 * The current interval for the {@link #goAhead} method.
033 *
034 * @serial
035 */
036 private Object m_oInterval;
037
038 /**
039 * The listeners registered with this timer.
040 *
041 * @serial
042 */
043 protected ListenerHelper m_lhListeners = new ListenerHelper();
044
045 /**
046 * The number of the current time stamp.
047 *
048 * @serial
049 */
050 private long m_lTimeStamps;
051
052 /**
053 * Create a new timer wich uses an instance of {@link Step Step} as the time object.
054 */
055 public StepTimer() {
056 this(new Step());
057 }
058
059 /**
060 * Create a new timer wich uses the given {@link Time Time} object.
061 *
062 * @param tTimeObject the time object to use
063 */
064 public StepTimer(Time tTimeObject) {
065 super();
066
067 m_tTime = tTimeObject;
068 m_oInterval = m_tTime.getDefaultInterval();
069 }
070
071 /**
072 * Set the time and fire a <code>timeSet</code> event.
073 *
074 * <p>The time has to be in a format that can be processed by the {@link Time Time} object.</p>
075 *
076 * @override Never
077 *
078 * @param oTime the time to set
079 *
080 * @exception IllegalArgumentException if the set time does not meet the time object's class or format
081 * requirements
082 */
083 public void setTime(Object oTime) throws IllegalArgumentException {
084 m_tTime.setTime(oTime);
085 fireTimeSet();
086 }
087
088 /**
089 * Get the current time. This is delegated to the {@link Time} object.
090 *
091 * @override Never
092 *
093 * @return an Object representing the current time, the exact type depends on the time object
094 */
095 public Object getTime() {
096 return m_tTime.getTime();
097 }
098
099 /**
100 * Returns the object that contains the time.
101 *
102 * @override Never
103 *
104 * @return the Time object.
105 */
106 public Time getTimeObject() {
107 return m_tTime;
108 }
109
110 /**
111 * Set the interval to be used by the {@link #goAhead goAhead()} method.
112 *
113 * <p>The given interval has to be of a proper type to be used with the time object's
114 * {@link Time#goAhead goAhead()} method.</p>
115 *
116 * @override Never
117 *
118 * @param oInterval the interval to be used
119 */
120 public void setInterval(Object oInterval) {
121 m_oInterval = oInterval;
122 fireIntervalSet();
123 }
124
125 /**
126 * Get the current interval.
127 *
128 * @override Never
129 *
130 * @return an Object representing the current interval
131 */
132 public Object getInterval() {
133 return m_oInterval;
134 }
135
136 /**
137 * Add a {@link sale.events.TimerListener TimerListener} which will receive
138 * {@link sale.events.TimerEvent TimerEvents} triggered by this timer.
139 *
140 * @override Never
141 *
142 * @param tlListener the listener to be registered.
143 */
144 public void addTimerListener(TimerListener tlListener) {
145 m_lhListeners.add(TimerListener.class, tlListener);
146 }
147
148 /**
149 * Remove the given {@link sale.events.TimerListener TimerListener}.
150 *
151 * @override Never
152 *
153 * @param tlListener the listener to be deregistered.
154 */
155 public void removeTimerListener(TimerListener tlListener) {
156 m_lhListeners.remove(TimerListener.class, tlListener);
157 }
158
159 /**
160 * Increase the time by the current interval.
161 *
162 * <p>If no interval has been set yet, the interval given by the {@link Time#getDefaultInterval()} method
163 * of the time object is used.</p>
164 *
165 * @override Never
166 *
167 * @exception IllegalArgumentException if the interval does not meet the time object's class or format
168 * requirements
169 */
170 public void goAhead() throws IllegalArgumentException {
171 m_tTime.goAhead(m_oInterval);
172 m_lTimeStamps = 0;
173 fireGoneAhead();
174 }
175
176 /**
177 * Create and return a fresh time stamp.
178 *
179 * @override Never
180 *
181 * @return a fresh time stamp.
182 */
183 public Comparable<String> getTimeStamp() {
184 return m_tTime.getTimeStamp(++m_lTimeStamps);
185 }
186
187 /**
188 * Fire a <code>timeSet</code> event.
189 *
190 * @override Never
191 */
192 protected void fireTimeSet() {
193 Object[] listeners = m_lhListeners.getListenerList();
194 TimerEvent e = null;
195
196 for (int i = listeners.length - 2; i >= 0; i -= 2) {
197 if (listeners[i] == TimerListener.class) {
198 if (e == null) {
199 e = new TimerEvent(this);
200 }
201 ((TimerListener)listeners[i + 1]).onTimeSet(e);
202 }
203 }
204 }
205
206 /**
207 * Fire an <code>intervalSet</code> event.
208 *
209 * @override Never
210 */
211 protected void fireIntervalSet() {
212 Object[] listeners = m_lhListeners.getListenerList();
213 TimerEvent e = null;
214
215 for (int i = listeners.length - 2; i >= 0; i -= 2) {
216 if (listeners[i] == TimerListener.class) {
217 if (e == null) {
218 e = new TimerEvent(this);
219 }
220 ((TimerListener)listeners[i + 1]).onIntervalSet(e);
221 }
222 }
223 }
224
225 /**
226 * Fire a <code>goneAhead</code> event.
227 *
228 * @override Never
229 */
230 protected void fireGoneAhead() {
231 Object[] listeners = m_lhListeners.getListenerList();
232 TimerEvent e = null;
233
234 for (int i = listeners.length - 2; i >= 0; i -= 2) {
235 if (listeners[i] == TimerListener.class) {
236 if (e == null) {
237 e = new TimerEvent(this);
238 }
239 ((TimerListener)listeners[i + 1]).onGoneAhead(e);
240 }
241 }
242 }
243 }