View Javadoc
1   package org.opentrafficsim.draw.graphs;
2   
3   import java.util.concurrent.BlockingQueue;
4   import java.util.concurrent.LinkedBlockingQueue;
5   import java.util.concurrent.TimeUnit;
6   
7   import nl.tudelft.simulation.dsol.logger.SimLogger;
8   
9   /**
10   * The GrapghUpdater can be used to repeatedly offer a value that is automatically processed in order of offering in a parallel
11   * Thread.
12   * <p>
13   * Copyright (c) 2013-2019 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved. <br>
14   * BSD-style license. See <a href="http://opentrafficsim.org/node/13">OpenTrafficSim License</a>.
15   * <p>
16   * @version $Revision$, $LastChangedDate$, by $Author$, initial version 13 okt. 2018 <br>
17   * @author <a href="http://www.tbm.tudelft.nl/averbraeck">Alexander Verbraeck</a>
18   * @author <a href="http://www.tudelft.nl/pknoppers">Peter Knoppers</a>
19   * @author <a href="http://www.transport.citg.tudelft.nl">Wouter Schakel</a>
20   * @param <T> type of value in queue
21   */
22  public class GraphUpdater<T>
23  {
24  
25      /** Queue of update times for executing Thread. */
26      private final BlockingQueue<T> queue = new LinkedBlockingQueue<>();
27  
28      /**
29       * Constructs and starts a thread that performs each given task from a queue.
30       * @param workerName String; name for the working thread
31       * @param invokingThread Thread; invoking thread, the worker will stop when this thread is interrupted
32       * @param updater Updater&lt;T&gt;; updater to perform with the queued value
33       */
34      public GraphUpdater(final String workerName, final Thread invokingThread, final Updater<T> updater)
35      {
36          new Thread(new Runnable()
37          {
38              /** {@inheritDoc} */
39              @SuppressWarnings({"synthetic-access"})
40              @Override
41              public void run()
42              {
43                  while (!invokingThread.isInterrupted())
44                  {
45                      try
46                      {
47                          T t = GraphUpdater.this.queue.poll(5, TimeUnit.SECONDS);
48                          if (t != null)
49                          {
50                              updater.update(t);
51                          }
52                      }
53                      catch (InterruptedException exception)
54                      {
55                          SimLogger.always().error(exception, "Worker {} thread stopped.", workerName);
56                          break;
57                      }
58                  }
59              }
60          }, workerName).start();
61      }
62  
63      /**
64       * Offer a next value to the queue.
65       * @param t T; next value to offer to the queue
66       */
67      public final void offer(final T t)
68      {
69          this.queue.offer(t);
70      }
71  
72      /**
73       * Functional interface for updates to perform.
74       * <p>
75       * Copyright (c) 2013-2019 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved.
76       * <br>
77       * BSD-style license. See <a href="http://opentrafficsim.org/node/13">OpenTrafficSim License</a>.
78       * <p>
79       * @version $Revision$, $LastChangedDate$, by $Author$, initial version 13 okt. 2018 <br>
80       * @author <a href="http://www.tbm.tudelft.nl/averbraeck">Alexander Verbraeck</a>
81       * @author <a href="http://www.tudelft.nl/pknoppers">Peter Knoppers</a>
82       * @author <a href="http://www.transport.citg.tudelft.nl">Wouter Schakel</a>
83       * @param <T> type of value in queue
84       */
85      @FunctionalInterface
86      interface Updater<T>
87      {
88          /**
89           * Perform an update.
90           * @param t T; value to update by
91           */
92          void update(T t);
93      }
94  
95      /** {@inheritDoc} */
96      @Override
97      public String toString()
98      {
99          return "GraphUpdater [queue=" + this.queue + "]";
100     }
101 
102 }