View Javadoc
1   package org.opentrafficsim.road.gtu.lane;
2   
3   import org.djutils.exceptions.Try;
4   import org.opentrafficsim.base.logger.Logger;
5   import org.opentrafficsim.core.gtu.Gtu;
6   import org.opentrafficsim.core.gtu.perception.Perception;
7   
8   /**
9    * Utility to make debugging on a specific GTU more convenient. There is a method {@code on()} for a GTU and for perception.
10   * Should neither be available within the context of a method that needs to be debugged, {@code onSub()} can be used in
11   * combination with {@code onSuper()} at a higher-level method with a GTU or perception. <i>This class requires the user to set
12   * a break point in the method {@code trigger()}.</i>
13   * <p>
14   * Copyright (c) 2013-2024 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved. <br>
15   * BSD-style license. See <a href="https://opentrafficsim.org/docs/license.html">OpenTrafficSim License</a>.
16   * </p>
17   * @author <a href="https://github.com/averbraeck">Alexander Verbraeck</a>
18   * @author <a href="https://github.com/peter-knoppers">Peter Knoppers</a>
19   * @author <a href="https://github.com/wjschakel">Wouter Schakel</a>
20   */
21  public final class Break
22  {
23  
24      /** Condition to allow or prevent breaking in lower-level functionality. */
25      private static boolean superCondition = false;
26  
27      /**
28       * Constructor.
29       */
30      private Break()
31      {
32          //
33      }
34  
35      /**
36       * Sets a break condition to true which is triggered by {@code onSub()} at a lower level where context is insufficient to
37       * determine the break condition.
38       * @param perception perception to obtain gtu from
39       * @param id GTU id to break on
40       * @param time time to break at (or after)
41       * @param additionalCondition additional condition
42       */
43      public static void onSuper(final Perception<?> perception, final String id, final double time,
44              final boolean additionalCondition)
45      {
46          Try.execute(() -> onSuper(perception.getGtu(), id, time, additionalCondition),
47                  "Trying to break on gtu, but gtu could not be obtained from perception.");
48      }
49  
50      /**
51       * Sets a break condition to true which is triggered by {@code onSub()} at a lower level where context is insufficient to
52       * determine the break condition.
53       * @param gtu GTU
54       * @param id GTU id to break on
55       * @param time time to break at (or after)
56       * @param additionalCondition additional condition
57       */
58      public static void onSuper(final Gtu gtu, final String id, final double time, final boolean additionalCondition)
59      {
60          superCondition = gtu.getId().equals(id) && gtu.getSimulator().getSimulatorTime().si >= time && additionalCondition;
61      }
62  
63      /**
64       * This method can be used if the context of a lower-level function does not contain the information on which to break. This
65       * method will only trigger a break if at a higher-level function where the context was sufficient, the break condition was
66       * set to true using {@code onSuper()}.
67       */
68      public static void onSub()
69      {
70          if (superCondition)
71          {
72              trigger();
73          }
74      }
75  
76      /**
77       * This method can be used if the context of a lower-level function does not contain the information on which to break. This
78       * method will only trigger a break if at a higher-level function where the context was sufficient, the break condition was
79       * set to true using {@code onSuper()}.
80       * @param additionalCondition additional condition
81       */
82      public static void onSub(final boolean additionalCondition)
83      {
84          if (superCondition && additionalCondition)
85          {
86              trigger();
87          }
88      }
89  
90      /**
91       * Break on perception and String of time.
92       * @param perception perception to obtain gtu from
93       * @param id GTU id to break on
94       * @param time time to break at (or after), in format ss, mm:ss or hh:mm:ss
95       * @param additionalCondition additional condition
96       */
97      public static void on(final Perception<?> perception, final String id, final String time, final boolean additionalCondition)
98      {
99          on(perception, id, timeFromString(time), additionalCondition);
100     }
101 
102     /**
103      * Returns a double representation of a String time.
104      * @param time string format, ss, mm:ss or hh:mm:ss
105      * @return double representation of a String time
106      */
107     private static double timeFromString(final String time)
108     {
109         int index = time.indexOf(":");
110         if (index < 0)
111         {
112             return Double.valueOf(time) - 1e-6;
113         }
114         int index2 = time.indexOf(":", index + 1);
115         double h;
116         double m;
117         double s;
118         if (index2 < 0)
119         {
120             h = 0;
121             m = Double.valueOf(time.substring(0, index));
122             s = Double.valueOf(time.substring(index + 1));
123         }
124         else
125         {
126             h = Double.valueOf(time.substring(0, index));
127             m = Double.valueOf(time.substring(index + 1, index2));
128             s = Double.valueOf(time.substring(index2 + 1));
129         }
130         return h * 3600.0 + m * 60.0 + s - 1e-6;
131     }
132 
133     /**
134      * Break on perception and double time.
135      * @param perception perception to obtain gtu from
136      * @param id GTU id to break on
137      * @param time time to break at (or after)
138      * @param additionalCondition additional condition
139      */
140     public static void on(final Perception<?> perception, final String id, final double time, final boolean additionalCondition)
141     {
142         Try.execute(() -> on(perception.getGtu(), id, time, additionalCondition),
143                 "Trying to break on gtu, but gtu could not be obtained from perception.");
144     }
145 
146     /**
147      * Break on GTU and String of time.
148      * @param gtu GTU
149      * @param id GTU id to break on
150      * @param time time to break at (or after), in format ss, mm:ss or hh:mm:ss
151      * @param additionalCondition additional condition
152      */
153     public static void on(final Gtu gtu, final String id, final String time, final boolean additionalCondition)
154     {
155         on(gtu, id, timeFromString(time), additionalCondition);
156     }
157 
158     /**
159      * Break on GTU and double time.
160      * @param gtu GTU
161      * @param id GTU id to break on
162      * @param time time to break at (or after)
163      * @param additionalCondition additional condition
164      */
165     public static void on(final Gtu gtu, final String id, final double time, final boolean additionalCondition)
166     {
167         if (gtu.getId().equals(id) && gtu.getSimulator().getSimulatorTime().si >= time && additionalCondition)
168         {
169             trigger();
170         }
171     }
172 
173     /**
174      * Method that is invoked on a break condition. A break-point here allows the user to debug specific situations.
175      */
176     private static void trigger()
177     {
178         Logger.ots().error("Break condition for debugging is true."); // SET BREAK POINT ON THIS LINE
179     }
180 
181 }