public class EventTimerThread extends java.lang.Object implements EventTimerThread_ifc, java.io.Closeable, InfoAppend
start() and close() are used from instances of EventWithDst, 
 TimeOrder and TimeOrder internally.
 They should not be invoked by an application directly. 
 But if any other event derived from EventObject is used then the methods 
 setStdEventProcessor(EventConsumer), storeEvent(EventObject) and maybe removeFromQueue(EventObject)
 should be used. 
 
 
  EventTimerThread myExecutionThread = new EventTimerThread("thread-name");
  myExecutionThread.start();
 
 On end of the application close() should be invoked to end the thread.
 EventWithDst from any other thread use this instance as argument for the event: 
 MyEventWithDst event = new MyEventWithDst(source, dst, myExecutionThread); //or: event.occupy(source, dst, myExecutionThread, ...) event.sendEvent();To add any other type of
EventObject you should set a setStdEventProcessor(EventConsumer). 
 Then use 
 myExecutionThread.storeEvent(eventObject);This class is used as time manager too. It manages and executes
TimeOrder 
 which are used especially for StateMachine,
 but it can execute TimeOrder in this thread too. To add a timeout event or a time order 
 use the methods of the TimeOrder.activateAt(long) etc:
 
 
  TimeOrder myTimeOrder = new TimeOrder("name", myExecutionThread) {
    QOverride protected void executeOrder(){ ...execution of the time order ...}
  };
  ...
  myTimeOrder.activate(100);  //in 100 milliseconds.
  
 That routine invokes the routine addTimeEntry(TimeOrder) of this class.
 ConcurrentLinkedQueue which is thread-safe to enqueue events
 from any thread with the method storeEvent(EventObject).
 Then Object.notify() is called to weak up the thread if it sleeps. Then the all stored events are dequeued
 and its execution routine of EventConsumer.processEvent(EventObject) is invoked. The events are processed one after another.
 The execution routine is usual a StateMachine but any other EventConsumer is able to use too. 
 TimeOrder are stored in another ConcurrentLinkedQueue. 
 The absolute time of the next execution is stored in the internal value of timeCheckNew. The thread sleeps either
 till this time is expired or till an event is given. If the time is expired all stored time orders are checked
 whether its time is elapsed. Then either the EventConsumer.processEvent(EventObject) is invoked 
 if an TimeOrder is given or a TimeOrder has a destination. Elsewhere the TimeOrder#doExecute 
 is invoked to execute the TimeOrder#executeOrder() in this thread.
 removeFromQueue(EventObject)
 is invoked if an event should be EventWithDst.occupyRecall(EventSource, boolean). That is if the event should be used
 newly.
 TimeOrder can be removed from execution with the method TimeOrder.deactivate().
 Adequate is done with removeTimeEntry(TimeOrder).| Modifier and Type | Field and Description | 
|---|---|
| protected boolean | bThreadRun | 
| private int | ctWaitEmptyQueue | 
| private int | debugPrintBit variable to control some System.out.printf debug outputs. | 
| (package private) int | debugPrintViewDelayedOnly for inspector or debug access: Use it to show delaying. | 
| private int | delayMaxThe delay [ms] for one step if nothing is to do. | 
| private EventConsumer | eventProcessor | 
| private java.util.concurrent.atomic.AtomicBoolean | extEventSetSet if any external event is set. | 
| protected int | maxCtWaitEmptyQueue | 
| private boolean | preserveRecursiveInfoAppend | 
| private java.util.concurrent.ConcurrentLinkedQueue<TimeOrder> | queueDelayedOrdersQueue of orders which are executed with delay yet. | 
| private java.util.concurrent.ConcurrentLinkedQueue<java.util.EventObject> | queueEventsQueue of orders which are executed with delay yet. | 
| private java.util.concurrent.ConcurrentLinkedQueue<TimeOrder> | queueOrdersToExecuteTemporary used instance for orders ready to execute while  runTimerorganizes the delayed orders. | 
| private java.lang.Runnable | runTimerInstance as Runnable contains invocation of  stepThread()and theObject.wait()with the calculated timeWait. | 
| protected boolean | startOnDemand | 
| protected char | stateThreadTimerState of the thread, used for debug and mutex mechanism. | 
| protected java.lang.String | threadName | 
| protected java.lang.Thread | threadTimerThe thread which executes delayed wake up. | 
| protected long | timeCheckNewtimestamp for a new time entry. | 
| private long | timeSleepThe time on start waiting | 
| static java.lang.String | versionVersion, license and history. | 
| Constructor and Description | 
|---|
| EventTimerThread(java.lang.String threadName)Creates the Manager for time orders. | 
| Modifier and Type | Method and Description | 
|---|---|
| char | addTimeEntry(TimeOrder order)Adds a timeout event or a time order with given execution time. | 
| private boolean | checkEventAndRun()Applies an events from the queue to the destination in the event thread. | 
| private int | checkTimeOrders()Check all time orders whether there are expired, or if not calculate the next time to check. | 
| void | close()Should only be called on end of the whole application to finish the timer thread. | 
| protected void | createThread_()This operation can be overridden if another thread organization, 
 especially another  stepThread()should be used. | 
| char | getState()Returns the current state of the thread. | 
| java.lang.CharSequence | infoAppend(java.lang.StringBuilder u)Info for debugging 
  This operation can be overridden for another thread organization. | 
| boolean | isBusy()Checks whether the thread is busy. | 
| boolean | isCurrentThread()Returns true if the current thread is the thread which is aggregate to this EventThread. | 
| void | notifyTimer()Wakes up the  runTimerqueue to execute delayed requests. | 
| boolean | removeFromQueue(java.util.EventObject ev)Removes this event from its queue if it is in the event queue. | 
| boolean | removeTimeEntry(TimeOrder order)Removes a time order, which was activated but it is not in the event execution queue. | 
| void | setStdEventProcessor(EventConsumer eventProcessor)Sets the event processor for all events which are not type of  EventWithDst. | 
| void | start()Creates and starts the thread. | 
| private void | startOrNotify() | 
| protected int | stepThread()The core run routine for the timer thread. | 
| boolean | storeEvent(java.util.EventObject ev)Stores an event in the queue, able to invoke from any thread. | 
| java.lang.String | toString() | 
| protected void | wakeup_()Wakes up the waiting thread because a new event or time entry is enqueues. | 
public static final java.lang.String version
TimeOrder.bHoldTimeorder to change data in time order, prevent processing.
 org.vishia.gral.base.GralMng as graphic thread.
   Hence some stuff is now protected, only a few operations are overridden, see there. 
   All non overridden operations are set to final now here.    
 delayMax now also valid if no time order was processed.
   Before, it was 1000 days. This is not problematically for event processing, 
   because an event wakes up the wait by runTimer.Object.notify() but it is stupid on debugging.  
 isBusy()
 timeCheckNew
 OrderListExecuter
 org.vishia.gral.base.GralGraphicThread,
   this class is the base class of them now. The algorithm is able to use outside of that graphic too.
 private int debugPrint
int debugPrintViewDelayed
protected final java.lang.String threadName
protected java.lang.Thread threadTimer
private EventConsumer eventProcessor
private final java.util.concurrent.ConcurrentLinkedQueue<java.util.EventObject> queueEvents
private final java.util.concurrent.ConcurrentLinkedQueue<TimeOrder> queueDelayedOrders
private final java.util.concurrent.ConcurrentLinkedQueue<TimeOrder> queueOrdersToExecute
runTimer organizes the delayed orders.
 This queue is empty outside running one step of runTimer().protected boolean bThreadRun
private int delayMax
protected long timeCheckNew
#addTimeOrder(TimeEvent, long)
 and the wait in the #run() operation.
 The default value is 10 seconds after now, because no time order may be added. 
 10 sec is the limited delay to run one step.private long timeSleep
protected char stateThreadTimer
addTimeEntry(TimeOrder) with delayed order.private final java.util.concurrent.atomic.AtomicBoolean extEventSet
protected boolean startOnDemand
private int ctWaitEmptyQueue
protected int maxCtWaitEmptyQueue
private boolean preserveRecursiveInfoAppend
private java.lang.Runnable runTimer
stepThread()
 and the Object.wait() with the calculated timeWait.
 Note desired for overridden implementation.public EventTimerThread(java.lang.String threadName)
start() at begin and close() on end of an application.executesTheOrder - true then the method #step(int, long) need not be called (not necessary) because the TimeOrder
   are executed from the threadTimer already. 
   #step(int, long) have to be called cyclically from any other thread.public final void setStdEventProcessor(EventConsumer eventProcessor)
EventWithDst. That events are executed with
 the given eventProcessor's method EventConsumer.processEvent(EventObject).
 This eventProcessor is not used for EventWithDst. They need a destination or they should be a TimeOrder.
 eventProcessor - the event processor.public final void start()
#storeEvent(EventCmdtype) was called.
 In that case the thread stops its execution if the event queue is empty and about 5 seconds
 are gone.protected void createThread_()
stepThread() should be used.
 Then just another Runnable implementation for the thread is used.public final boolean storeEvent(java.util.EventObject ev)
storeEvent in interface EventThread_ifcev - private void startOrNotify()
protected void wakeup_()
org.vishia.gral.base.GralMng.public void close()
ConnectionExecThread is given as Argument of @link EventTimerThread#TimeOrderMng(ConnectionExecThread)
 and this instance implements the @link ConnectionExecThread#isRunning() method. If that method returns false
 then the timer thread is finished too.
 close in interface java.io.Closeableclose in interface java.lang.AutoCloseableCloseable.close()public final char addTimeEntry(TimeOrder order)
EventTimerThread_ifcTimeOrder.activateAt(long) etc. That routines calls this method internally already.
 Therefore this method should not be called by an application directly. It is only a rule to implement.addTimeEntry in interface EventTimerThread_ifcpublic final boolean removeTimeEntry(TimeOrder order)
ConcurrentLinkedQueue.removeTimeEntry in interface EventTimerThread_ifcorder - public final boolean removeFromQueue(java.util.EventObject ev)
EventWithDst is found in the queue, it is designated with stateOfEvent = 'a'
 This operation is thread safe. Either the event is found and removed, or it is not found because it is
 either in execution yet or it is not queued. The event queue is a ConcurrentLinkedQueue.removeFromQueue in interface EventThread_ifcev - The event which should be dequeuedpublic boolean isBusy()
EventThread_ifcTimeOrder waits for its finishing. If an execution remains in process because debugging, this method returns true.isBusy in interface EventThread_ifcprivate boolean checkEventAndRun()
private int checkTimeOrders()
queueDelayedOrders
 regarding changing also for and because TimeOrder.activateAt(long, long), which uses this as mutex.
 #evDst() is given the EventConsumer.processEvent(java.util.EventObject) is called
 though this instance may be a timeOrder. This method can enqueue this instance in another queue for execution
 in any other thread which invokes then TimeOrder#doExecute().
 TimeOrder and the #evDst is not given by constructor
 then the TimeOrder#doExecute() is called to execute the time order.
 #activate(int) etc. enqueues this instance newly
 with a new time for elapsing. It is executed newly therefore.protected final int stepThread()
public final boolean isCurrentThread()
#run() method has called this method.isCurrentThread in interface EventThread_ifcpublic final char getState()
public void notifyTimer()
runTimer queue to execute delayed requests.
 public java.lang.CharSequence infoAppend(java.lang.StringBuilder u)
infoAppend in interface InfoAppendu - if not null then the info is appended to u, u is returned.
   public java.lang.String toString()
toString in class java.lang.Object