001package jmri.implementation;
002
003import java.io.File;
004import java.util.Date;
005import java.util.List;
006
007import javax.annotation.Nonnull;
008import javax.script.ScriptException;
009import javax.swing.Timer;
010
011import jmri.*;
012import jmri.implementation.DefaultConditional.TimeSensor;
013import jmri.implementation.DefaultConditional.TimeTurnout;
014import jmri.jmrit.Sound;
015import jmri.jmrit.audio.AudioListener;
016import jmri.jmrit.audio.AudioSource;
017import jmri.jmrit.entryexit.DestinationPoints;
018import jmri.jmrit.entryexit.EntryExitPairs;
019import jmri.jmrit.logix.OBlock;
020import jmri.jmrit.logix.Warrant;
021import jmri.script.JmriScriptEngineManager;
022import jmri.script.swing.ScriptOutput;
023
024/**
025 * Helper class for DefaultConditional that executes the  actions of a
026 * DefaultConditional.
027 * @author Daniel Bergqvist (C) 2021
028 */
029public class DefaultConditionalExecute {
030
031    private final DefaultConditional conditional;
032
033    DefaultConditionalExecute(@Nonnull DefaultConditional conditional) {
034        this.conditional = conditional;
035    }
036
037    void setTurnout(@Nonnull ConditionalAction action, Turnout t,
038            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
039        if (t == null) {
040            errorList.add("invalid turnout name in action - " + action.getDeviceName());  // NOI18N
041        } else {
042            int act = action.getActionData();
043            if (act == Route.TOGGLE) {
044                int state = t.getKnownState();
045                if (state == Turnout.CLOSED) {
046                    act = Turnout.THROWN;
047                } else {
048                    act = Turnout.CLOSED;
049                }
050            }
051            t.setCommandedState(act);
052            increaseCounter(actionCount);
053        }
054    }
055
056    void delayedTurnout(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
057            @Nonnull TimeTurnout timeTurnout, boolean reset, String devName) {
058        if (reset) {
059            action.stopTimer();
060        }
061        if (!action.isTimerActive()) {
062            // Create a timer if one does not exist
063            Timer timer = action.getTimer();
064            if (timer == null) {
065                action.setListener(timeTurnout);
066                timer = new Timer(2000, action.getListener());
067                timer.setRepeats(true);
068            }
069            // Start the Timer to set the turnout
070            int value = conditional.getMillisecondValue(action);
071            if (value < 0) {
072                return;
073            }
074            timer.setInitialDelay(value);
075            action.setTimer(timer);
076            action.startTimer();
077            increaseCounter(actionCount);
078        } else {
079            log.warn("timer already active on request to start delayed turnout action - {}", devName);
080        }
081    }
082
083    void cancelTurnoutTimers(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
084            @Nonnull List<String> errorList, String devName) {
085        ConditionalManager cmg = InstanceManager.getDefault(ConditionalManager.class);
086        java.util.Iterator<Conditional> iter = cmg.getNamedBeanSet().iterator();
087        while (iter.hasNext()) {
088            String sname = iter.next().getSystemName();
089
090            Conditional c = cmg.getBySystemName(sname);
091            if (c == null) {
092                errorList.add("Conditional null during cancel turnout timers for "  // NOI18N
093                        + action.getDeviceName());
094                continue; // no more processing of this one
095            }
096
097            c.cancelTurnoutTimer(devName);
098            increaseCounter(actionCount);
099        }
100    }
101
102    void lockTurnout(@Nonnull ConditionalAction action, Turnout tl, @Nonnull Reference<Integer> actionCount,
103            @Nonnull List<String> errorList) {
104        if (tl == null) {
105            errorList.add("invalid turnout name in action - " + action.getDeviceName());  // NOI18N
106        } else {
107            int act = action.getActionData();
108            if (act == Route.TOGGLE) {
109                if (tl.getLocked(Turnout.CABLOCKOUT)) {
110                    act = Turnout.UNLOCKED;
111                } else {
112                    act = Turnout.LOCKED;
113                }
114            }
115            if (act == Turnout.LOCKED) {
116                tl.setLocked(Turnout.CABLOCKOUT + Turnout.PUSHBUTTONLOCKOUT, true);
117            } else if (act == Turnout.UNLOCKED) {
118                tl.setLocked(Turnout.CABLOCKOUT + Turnout.PUSHBUTTONLOCKOUT, false);
119            }
120            increaseCounter(actionCount);
121        }
122    }
123
124    void setSignalAppearance(@Nonnull ConditionalAction action, SignalHead h,
125            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
126        if (h == null) {
127            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
128        } else {
129            h.setAppearance(action.getActionData());
130            increaseCounter(actionCount);
131        }
132    }
133
134    void setSignalHeld(@Nonnull ConditionalAction action, SignalHead h,
135            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
136        if (h == null) {
137            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
138        } else {
139            h.setHeld(true);
140            increaseCounter(actionCount);
141        }
142    }
143
144    void clearSignalHeld(@Nonnull ConditionalAction action, SignalHead h,
145            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
146        if (h == null) {
147            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
148        } else {
149            h.setHeld(false);
150            increaseCounter(actionCount);
151        }
152    }
153
154    void setSignalDark(@Nonnull ConditionalAction action, SignalHead h,
155            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
156        if (h == null) {
157            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
158        } else {
159            h.setLit(false);
160            increaseCounter(actionCount);
161        }
162    }
163
164    void setSignalLit(@Nonnull ConditionalAction action, SignalHead h,
165            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
166        if (h == null) {
167            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
168        } else {
169            h.setLit(true);
170            increaseCounter(actionCount);
171        }
172    }
173
174    void triggerRoute(@Nonnull ConditionalAction action, Route r,
175            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
176        if (r == null) {
177            errorList.add("invalid Route name in action - " + action.getDeviceName());  // NOI18N
178        } else {
179            r.setRoute();
180            increaseCounter(actionCount);
181        }
182    }
183
184    void setSensor(@Nonnull ConditionalAction action, Sensor sn,
185            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList, String devName) {
186        if (sn == null) {
187            errorList.add("invalid Sensor name in action - " + action.getDeviceName());  // NOI18N
188        } else {
189            int act = action.getActionData();
190            if (act == Route.TOGGLE) {
191                int state = sn.getState();
192                if (state == Sensor.ACTIVE) {
193                    act = Sensor.INACTIVE;
194                } else {
195                    act = Sensor.ACTIVE;
196                }
197            }
198            try {
199                sn.setKnownState(act);
200                increaseCounter(actionCount);
201            } catch (JmriException e) {
202                log.warn("Exception setting Sensor {} in action", devName);  // NOI18N
203            }
204        }
205    }
206
207    void delayedSensor(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
208            @Nonnull TimeSensor timeSensor, int delay, boolean reset, String devName) {
209        if (reset) {
210            action.stopTimer();
211        }
212        if (!action.isTimerActive()) {
213            // Create a timer if one does not exist
214            Timer timer = action.getTimer();
215            if (timer == null) {
216                action.setListener(timeSensor);
217                timer = new Timer(2000, action.getListener());
218                timer.setRepeats(true);
219            }
220            // Start the Timer to set the sensor
221            if (delay < 0) {
222                return;
223            }
224            timer.setInitialDelay(delay);
225            action.setTimer(timer);
226            action.startTimer();
227            increaseCounter(actionCount);
228        } else {
229            log.warn("timer already active on request to start delayed sensor action - {}", devName);
230        }
231    }
232
233    void cancelSensorTimers(@Nonnull ConditionalAction action,
234            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList, String devName) {
235        ConditionalManager cm = InstanceManager.getDefault(ConditionalManager.class);
236        java.util.Iterator<Conditional> itr = cm.getNamedBeanSet().iterator();
237        while (itr.hasNext()) {
238            String sname = itr.next().getSystemName();
239            Conditional c = cm.getBySystemName(sname);
240            if (c == null) {
241                errorList.add("Conditional null during cancel sensor timers for "  // NOI18N
242                        + action.getDeviceName());
243                continue; // no more processing of this one
244            }
245
246            c.cancelSensorTimer(devName);
247            increaseCounter(actionCount);
248        }
249    }
250
251    void setLight(@Nonnull ConditionalAction action, Light lgt,
252            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
253        if (lgt == null) {
254            errorList.add("invalid light name in action - " + action.getDeviceName());  // NOI18N
255        } else {
256            int act = action.getActionData();
257            if (act == Route.TOGGLE) {
258                int state = lgt.getState();
259                if (state == Light.ON) {
260                    act = Light.OFF;
261                } else {
262                    act = Light.ON;
263                }
264            }
265            lgt.setState(act);
266            increaseCounter(actionCount);
267        }
268    }
269
270    void setLightIntensity(@Nonnull ConditionalAction action, Light lgt, int intensity,
271            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
272        if (lgt == null) {
273            errorList.add("invalid light name in action - " + action.getDeviceName());  // NOI18N
274        } else {
275            try {
276                if (intensity < 0) {
277                    return;
278                }
279                if (lgt instanceof VariableLight) {
280                    ((VariableLight)lgt).setTargetIntensity((intensity) / 100.0);
281                } else {
282                    lgt.setState(intensity > 0.5 ? Light.ON : Light.OFF);
283                }
284                increaseCounter(actionCount);
285            } catch (IllegalArgumentException e) {
286                errorList.add("Exception in set light intensity action - " + action.getDeviceName());  // NOI18N
287            }
288        }
289    }
290
291    void setLightTransitionTime(@Nonnull ConditionalAction action, Light lgt, int time,
292            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
293        if (lgt == null) {
294            errorList.add("invalid light name in action - " + action.getDeviceName());  // NOI18N
295        } else {
296            try {
297                if (time  < 0) {
298                    return;
299                }
300                if (lgt instanceof VariableLight) {
301                    ((VariableLight)lgt).setTransitionTime(time );
302                }
303                increaseCounter(actionCount);
304            } catch (IllegalArgumentException e) {
305                errorList.add("Exception in set light transition time action - " + action.getDeviceName());  // NOI18N
306            }
307        }
308    }
309
310    void setMemory(@Nonnull ConditionalAction action, Memory m,
311            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
312        if (m == null) {
313            errorList.add("invalid memory name in action - " + action.getDeviceName());  // NOI18N
314        } else {
315            m.setValue(action.getActionString());
316            increaseCounter(actionCount);
317        }
318    }
319
320    void copyMemory(@Nonnull ConditionalAction action, Memory mFrom, Memory mTo,
321            String actionStr, @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
322        if (mFrom == null) {
323            errorList.add("invalid memory name in action - " + action.getDeviceName());  // NOI18N
324        } else {
325            if (mTo == null) {
326                errorList.add("invalid memory name in action - " + action.getActionString());  // NOI18N
327            } else {
328                mTo.setValue(mFrom.getValue());
329                increaseCounter(actionCount);
330            }
331        }
332    }
333
334    void enableLogix(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
335            @Nonnull List<String> errorList, String devName) {
336        Logix x = InstanceManager.getDefault(LogixManager.class).getLogix(devName);
337        if (x == null) {
338            errorList.add("invalid logix name in action - " + action.getDeviceName());  // NOI18N
339        } else {
340            x.setEnabled(true);
341            increaseCounter(actionCount);
342        }
343    }
344
345    void disableLogix(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
346            @Nonnull List<String> errorList, String devName) {
347        Logix x = InstanceManager.getDefault(LogixManager.class).getLogix(devName);
348        if (x == null) {
349            errorList.add("invalid logix name in action - " + action.getDeviceName());  // NOI18N
350        } else {
351            x.setEnabled(false);
352            increaseCounter(actionCount);
353        }
354    }
355
356    void playSound(@Nonnull ConditionalAction action, String actionStr,
357            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
358        String path = actionStr;
359        if (!path.isEmpty()) {
360            Sound sound = action.getSound();
361            if (sound == null) {
362                try {
363                    sound = new Sound(path);
364                } catch (NullPointerException ex) {
365                    errorList.add("invalid path to sound: " + path);  // NOI18N
366                }
367            }
368            if (sound != null) {
369                sound.play();
370            }
371            increaseCounter(actionCount);
372        }
373    }
374
375    void runScript(@Nonnull ConditionalAction action, @Nonnull String actionStr,
376            @Nonnull Reference<Integer> actionCount) {
377        if (!(actionStr.isEmpty())) {
378            JmriScriptEngineManager.getDefault().runScript(new File(jmri.util.FileUtil.getExternalFilename(actionStr)));
379            increaseCounter(actionCount);
380        }
381    }
382
383    @SuppressWarnings({"deprecation"})  // date.setHours, date.setMinutes, date.setSeconds
384    void setFastClockTime(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount) {
385        Date date = InstanceManager.getDefault(Timebase.class).getTime();
386        date.setHours(action.getActionData() / 60);
387        date.setMinutes(action.getActionData() - ((action.getActionData() / 60) * 60));
388        date.setSeconds(0);
389        InstanceManager.getDefault(Timebase.class).userSetTime(date);
390        increaseCounter(actionCount);
391    }
392
393    void startFastClock(@Nonnull Reference<Integer> actionCount) {
394        InstanceManager.getDefault(Timebase.class).setRun(true);
395        increaseCounter(actionCount);
396    }
397
398    void stopFastClock(@Nonnull Reference<Integer> actionCount) {
399        InstanceManager.getDefault(Timebase.class).setRun(false);
400        increaseCounter(actionCount);
401    }
402
403    void controlAudio(@Nonnull ConditionalAction action, String devName) {
404        Audio audio = InstanceManager.getDefault(AudioManager.class).getAudio(devName);
405        if (audio == null) {
406            return;
407        }
408        if (audio.getSubType() == Audio.SOURCE) {
409            AudioSource audioSource = (AudioSource) audio;
410            switch (action.getActionData()) {
411                case Audio.CMD_PLAY:
412                    audioSource.play();
413                    break;
414                case Audio.CMD_STOP:
415                    audioSource.stop();
416                    break;
417                case Audio.CMD_PLAY_TOGGLE:
418                    audioSource.togglePlay();
419                    break;
420                case Audio.CMD_PAUSE:
421                    audioSource.pause();
422                    break;
423                case Audio.CMD_RESUME:
424                    audioSource.resume();
425                    break;
426                case Audio.CMD_PAUSE_TOGGLE:
427                    audioSource.togglePause();
428                    break;
429                case Audio.CMD_REWIND:
430                    audioSource.rewind();
431                    break;
432                case Audio.CMD_FADE_IN:
433                    audioSource.fadeIn();
434                    break;
435                case Audio.CMD_FADE_OUT:
436                    audioSource.fadeOut();
437                    break;
438                case Audio.CMD_RESET_POSITION:
439                    audioSource.resetCurrentPosition();
440                    break;
441                default:
442                    break;
443            }
444        } else if (audio.getSubType() == Audio.LISTENER) {
445            AudioListener audioListener = (AudioListener) audio;
446            switch (action.getActionData()) {
447                case Audio.CMD_RESET_POSITION:
448                    audioListener.resetCurrentPosition();
449                    break;
450                default:
451                    break; // nothing needed for others
452            }
453        }
454    }
455
456    void jythonCommand(@Nonnull ConditionalAction action, String actionStr, @Nonnull Reference<Integer> actionCount) {
457        if (!(actionStr.isEmpty())) {
458            // add the text to the output frame
459            ScriptOutput.writeScript(actionStr);
460            // and execute
461
462            javax.script.ScriptEngine se =  JmriScriptEngineManager.getDefault()
463                .getEngine(JmriScriptEngineManager.JYTHON);
464            if (se!=null) {
465                try {
466                    JmriScriptEngineManager.getDefault().eval(actionStr, se);
467                } catch (ScriptException ex) {
468                    log.error("Error executing script:", ex);  // NOI18N
469                }
470            } else {
471                log.error("Error getting default ScriptEngine");
472            }
473            increaseCounter(actionCount);
474        }
475    }
476
477    void allocateWarrantRoute(@Nonnull ConditionalAction action, Warrant w,
478            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
479        if (w == null) {
480            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
481        } else {
482            String msg = w.allocateRoute(false, null);
483            if (msg != null) {
484                log.info("Warrant {} - {}", action.getDeviceName(), msg);  // NOI18N
485            }
486            increaseCounter(actionCount);
487        }
488    }
489
490    void deallocateWarrantRoute(@Nonnull ConditionalAction action, Warrant w,
491            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
492        if (w == null) {
493            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
494        } else {
495            w.deAllocate();
496            increaseCounter(actionCount);
497        }
498    }
499
500    void setRouteTurnouts(@Nonnull ConditionalAction action, Warrant w,
501            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
502        if (w == null) {
503            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
504        } else {
505            String msg = w.setRoute(false, null);
506            if (msg != null) {
507                log.info("Warrant {} unable to Set Route - {}", action.getDeviceName(), msg);  // NOI18N
508            }
509            increaseCounter(actionCount);
510        }
511    }
512
513    void setTrainId(@Nonnull ConditionalAction action, Warrant w, String actionStr,
514            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
515        if (w == null) {
516            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
517        } else {
518            if (w.getRunMode() != Warrant.MODE_NONE) {
519                errorList.add("Cannot set when Warrant is running - " + action.getActionString());  // NOI18N
520            } else if(!w.getSpeedUtil().setAddress(actionStr)) {
521                errorList.add("invalid train ID in action - " + action.getDeviceName());  // NOI18N
522            }
523            increaseCounter(actionCount);
524        }
525    }
526
527    void setTrainName(@Nonnull ConditionalAction action, Warrant w, String actionStr,
528            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
529        if (w == null) {
530            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
531        } else {
532            w.setTrainName(actionStr);
533            increaseCounter(actionCount);
534        }
535    }
536
537    void getTrainLocation(@Nonnull ConditionalAction action, Warrant w, Memory mTo, String actionStr,
538            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
539        if (w == null) {
540            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
541        } else {
542            if (mTo == null) {
543                errorList.add("invalid memory name in action - " + action.getActionString());  // NOI18N
544            } else {
545                mTo.setValue(w.getCurrentBlockName());
546                increaseCounter(actionCount);
547            }
548        }
549    }
550
551    void autoRunWarrant(@Nonnull ConditionalAction action, Warrant w,
552            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
553        if (w == null) {
554            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
555        } else {
556            jmri.jmrit.logix.WarrantTableFrame frame = jmri.jmrit.logix.WarrantTableFrame.getDefault();
557            String err = frame.runTrain(w, Warrant.MODE_RUN);
558            if (err != null) {
559                errorList.add("runAutoTrain error - " + err);  // NOI18N
560                w.stopWarrant(true, true);
561            }
562            increaseCounter(actionCount);
563        }
564    }
565
566    void manualRunWarrant(@Nonnull ConditionalAction action, Warrant w,
567            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
568        if (w == null) {
569            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
570        } else {
571            if (w.getRunMode() != Warrant.MODE_NONE) {
572                errorList.add("Cannot set when Warrant is running - " + action.getActionString());  // NOI18N
573            } else {
574                String err = w.setRoute(false, null);
575                if (err == null) {
576                    err = w.setRunMode(Warrant.MODE_MANUAL, null, null, null, false);
577                }
578                if (err != null) {
579                    errorList.add("runManualTrain error - " + err);  // NOI18N
580                }
581            }
582            increaseCounter(actionCount);
583        }
584    }
585
586    void controlTrain(@Nonnull ConditionalAction action, Warrant w,
587            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList, String devName) {
588        if (w == null) {
589            errorList.add("invalid Warrant name in action - " + action.getDeviceName());  // NOI18N
590        } else {
591            if (!w.controlRunTrain(action.getActionData())) {
592                log.info("Train {} not running  - {}", w.getSpeedUtil().getRosterId(), devName);  // NOI18N
593            }
594            increaseCounter(actionCount);
595        }
596    }
597
598    void setSignalMastAspect(@Nonnull ConditionalAction action, SignalMast f,
599            String actionStr, @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
600        if (f == null) {
601            errorList.add("invalid Signal Mast name in action - " + action.getDeviceName());  // NOI18N
602        } else {
603            f.setAspect(actionStr);
604            increaseCounter(actionCount);
605        }
606    }
607
608    void setSignalMastHeld(@Nonnull ConditionalAction action, SignalMast f,
609            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
610        if (f == null) {
611            errorList.add("invalid Signal Mast name in action - " + action.getDeviceName());  // NOI18N
612        } else {
613            f.setHeld(true);
614            increaseCounter(actionCount);
615        }
616    }
617
618    void clearSignalMastHeld(@Nonnull ConditionalAction action, SignalMast f,
619            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
620        if (f == null) {
621            errorList.add("invalid Signal Mast name in action - " + action.getDeviceName());  // NOI18N
622        } else {
623            f.setHeld(false);
624            increaseCounter(actionCount);
625        }
626    }
627
628    void setSignalMastDark(@Nonnull ConditionalAction action, SignalMast f,
629            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
630        if (f == null) {
631            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
632        } else {
633            f.setLit(false);
634            increaseCounter(actionCount);
635        }
636    }
637
638    void setSignalMastLit(@Nonnull ConditionalAction action, SignalMast f,
639            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
640        if (f == null) {
641            errorList.add("invalid Signal Head name in action - " + action.getDeviceName());  // NOI18N
642        } else {
643            f.setLit(true);
644            increaseCounter(actionCount);
645        }
646    }
647
648    void setBlockValue(@Nonnull ConditionalAction action, OBlock b, String actionStr,
649            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
650        if (b == null) {
651            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
652        } else {
653            b.setValue(actionStr);
654            increaseCounter(actionCount);
655        }
656    }
657
658    void setBlockError(@Nonnull ConditionalAction action, OBlock b,
659            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
660        if (b == null) {
661            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
662        } else {
663            b.setError(true);
664            increaseCounter(actionCount);
665        }
666    }
667
668    void clearBlockError(@Nonnull ConditionalAction action, OBlock b, @Nonnull List<String> errorList) {
669        if (b == null) {
670            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
671        } else {
672            b.setError(false);
673        }
674    }
675
676    void deallocateBlock(@Nonnull ConditionalAction action, OBlock b,
677            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
678        if (b == null) {
679            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
680        } else {
681            b.deAllocate(null);
682            increaseCounter(actionCount);
683        }
684    }
685
686    void setBlockOutOfService(@Nonnull ConditionalAction action, OBlock b,
687            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
688        if (b == null) {
689            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
690        } else {
691            b.setOutOfService(true);
692            increaseCounter(actionCount);
693        }
694    }
695
696    void setBlockInService(@Nonnull ConditionalAction action, OBlock b,
697            @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
698        if (b == null) {
699            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
700        } else {
701            b.setOutOfService(false);
702            increaseCounter(actionCount);
703        }
704    }
705
706    void getBlockTrainName(@Nonnull ConditionalAction action, OBlock b,
707            Memory mTo, String actionStr, @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
708        if (b == null) {
709            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
710        } else {
711            if (mTo == null) {
712                errorList.add("invalid memory name in action - " + action.getActionString());  // NOI18N
713            } else {
714                String name = (String)b.getValue();
715                if (name == null) {
716                    name = " ";
717                }
718                mTo.setValue(name);
719                increaseCounter(actionCount);
720            }
721        }
722    }
723
724    void getBlockWarrant(@Nonnull ConditionalAction action, OBlock b, Memory mTo,
725            String actionStr, @Nonnull Reference<Integer> actionCount, @Nonnull List<String> errorList) {
726        if (b == null) {
727            errorList.add("invalid Block name in action - " + action.getDeviceName());  // NOI18N
728        } else {
729            if (mTo == null) {
730                errorList.add("invalid memory name in action - " + action.getActionString());  // NOI18N
731            } else {
732                Warrant w = b.getWarrant();
733                String name;
734                if (w != null) {
735                    name = w.getDisplayName();
736                } else {
737                    name = " ";
738                }
739                mTo.setValue(name);
740                increaseCounter(actionCount);
741            }
742        }
743    }
744
745    void setNXPairEnabled(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
746            @Nonnull List<String> errorList, String devName) {
747        DestinationPoints dp = InstanceManager.getDefault(EntryExitPairs.class).getNamedBean(devName);
748        if (dp == null) {
749            errorList.add("Invalid NX Pair name in action - " + action.getDeviceName());  // NOI18N
750        } else {
751            dp.setEnabled(true);
752            increaseCounter(actionCount);
753        }
754    }
755
756    void setNXPairDisabled(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
757            @Nonnull List<String> errorList, String devName) {
758        DestinationPoints dp = InstanceManager.getDefault(EntryExitPairs.class).getNamedBean(devName);
759        if (dp == null) {
760            errorList.add("Invalid NX Pair name in action - " + action.getDeviceName());  // NOI18N
761        } else {
762            dp.setEnabled(false);
763            increaseCounter(actionCount);
764        }
765    }
766
767    void setNXPairSegment(@Nonnull ConditionalAction action, @Nonnull Reference<Integer> actionCount,
768            @Nonnull List<String> errorList, String devName) {
769        DestinationPoints dp = InstanceManager.getDefault(EntryExitPairs.class).getNamedBean(devName);
770        if (dp == null) {
771            errorList.add("Invalid NX Pair name in action - " + action.getDeviceName());  // NOI18N
772        } else {
773            InstanceManager.getDefault(EntryExitPairs.class).
774                    setSingleSegmentRoute(devName);
775            increaseCounter(actionCount);
776        }
777    }
778
779    private void increaseCounter(@Nonnull Reference<Integer> actionCount) {
780        // actionCount.get() is never null, but Spotbugs doesn't know that
781        Integer value = actionCount.get();
782        actionCount.set(value != null ? value+1 : 0);
783    }
784
785    private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(DefaultConditionalExecute.class);
786}