@@ -479,74 +479,74 @@ export class NodeService implements OnDestroy {
479479    trainrunSection . setTargetPortId ( targetPortId ) ; 
480480  } 
481481
482-   hasPathAnyDepartureOrArrivalTimeLock ( node : Node ,  trainrunSection : TrainrunSection ) : boolean  { 
483-     const  iterator  =  this . trainrunService . getIterator ( node ,  trainrunSection ) ; 
484-     while  ( iterator . hasNext ( ) )  { 
485-       iterator . next ( ) ; 
486-       const  currentTrainrunSection  =  iterator . current ( ) . trainrunSection ; 
487-       if  ( 
488-         currentTrainrunSection . getSourceDepartureLock ( )  || 
489-         currentTrainrunSection . getTargetArrivalLock ( ) 
490-       )  { 
491-         return  true ; 
482+   propagateTimes ( nodeId : number ,  transitionId : number ,  isForward : boolean )  { 
483+     const  node  =  this . getNodeFromId ( nodeId ) ; 
484+     const  sections  =  node . getTrainrunSections ( transitionId ) ; 
485+     const  node1  =  node . getOppositeNode ( sections . trainrunSection1 ) ; 
486+     const  node2  =  node . getOppositeNode ( sections . trainrunSection2 ) ; 
487+ 
488+     let  isSection1Locked  =  false ; 
489+     let  isSection2Locked  =  false ; 
490+     // Note: the source->target chain allows to check only the source or target locks based on isForward value 
491+     if  ( isForward )  { 
492+       // Forward propagation (A->B->C): check A and B sides locks (sourceDepartures) 
493+       isSection1Locked  =  sections . trainrunSection1 . getSourceDepartureLock ( ) ; 
494+       isSection2Locked  =  sections . trainrunSection2 . getSourceDepartureLock ( ) ; 
495+ 
496+       // order is important: section1 then section2 
497+       if  ( ! isSection1Locked )  { 
498+         this . trainrunSectionService . iterateAlongTrainrunUntilEndAndPropagateTime ( 
499+           node1 , 
500+           sections . trainrunSection1 . getId ( ) , 
501+         ) ; 
502+       } 
503+       if  ( ! isSection2Locked )  { 
504+         this . trainrunSectionService . iterateAlongTrainrunUntilEndAndPropagateTime ( 
505+           node2 , 
506+           sections . trainrunSection2 . getId ( ) , 
507+         ) ; 
508+       } 
509+     }  else  { 
510+       // Backward propagation (A<-B<-C): check B and C sides locks (targetDepartures) 
511+       isSection1Locked  =  sections . trainrunSection1 . getTargetDepartureLock ( ) ; 
512+       isSection2Locked  =  sections . trainrunSection2 . getTargetDepartureLock ( ) ; 
513+ 
514+       // order is important: section2 then section1 
515+       if  ( ! isSection2Locked )  { 
516+         this . trainrunSectionService . iterateAlongTrainrunUntilEndAndPropagateTime ( 
517+           node2 , 
518+           sections . trainrunSection2 . getId ( ) , 
519+         ) ; 
520+       } 
521+       if  ( ! isSection1Locked )  { 
522+         this . trainrunSectionService . iterateAlongTrainrunUntilEndAndPropagateTime ( 
523+           node1 , 
524+           sections . trainrunSection1 . getId ( ) , 
525+         ) ; 
492526      } 
493527    } 
494-     return  false ; 
495-   } 
496- 
497-   toggleNonStop ( nodeId : number ,  transitionId : number )  { 
498-     const  node  =  this . getNodeFromId ( nodeId ) ; 
499-     node . toggleNonStop ( transitionId ) ; 
500-     const  trainrunSections  =  node . getTrainrunSections ( transitionId ) ; 
501-     const  node1  =  node . getOppositeNode ( trainrunSections . trainrunSection1 ) ; 
502-     const  node2  =  node . getOppositeNode ( trainrunSections . trainrunSection2 ) ; 
503-     const  isForwardPathLocked  =  this . hasPathAnyDepartureOrArrivalTimeLock ( 
504-       node1 , 
505-       trainrunSections . trainrunSection1 , 
506-     ) ; 
507-     const  isBackwardPathLocked  =  this . hasPathAnyDepartureOrArrivalTimeLock ( 
508-       node2 , 
509-       trainrunSections . trainrunSection2 , 
510-     ) ; 
511528
512-     if  ( ! isForwardPathLocked )  { 
513-       this . trainrunSectionService . iterateAlongTrainrunUntilEndAndPropagateTime ( 
514-         node1 , 
515-         trainrunSections . trainrunSection1 . getId ( ) , 
516-       ) ; 
517-     } 
518-     if  ( ! isBackwardPathLocked )  { 
519-       this . trainrunSectionService . iterateAlongTrainrunUntilEndAndPropagateTime ( 
520-         node2 , 
521-         trainrunSections . trainrunSection2 . getId ( ) , 
522-       ) ; 
529+     if  ( isSection1Locked )  { 
530+       this . createTransitionWarning ( sections . trainrunSection1 ,  node ) ; 
523531    } 
524- 
525-     if  ( isForwardPathLocked  &&  isBackwardPathLocked )  { 
526-       const  warningTitle  =  $localize `:@@app.services.data.node.transit-modified.title:Transition changed` ; 
527-       const  warningDescription  =  $localize `:@@app.services.data.node.transit-modified.description:Times cannot be adjusted, lock found on both sides` ; 
528-       this . trainrunSectionService . setWarningOnNode ( 
529-         trainrunSections . trainrunSection1 . getId ( ) , 
530-         node . getId ( ) , 
531-         warningTitle , 
532-         warningDescription , 
533-       ) ; 
534-       this . trainrunSectionService . setWarningOnNode ( 
535-         trainrunSections . trainrunSection2 . getId ( ) , 
536-         node . getId ( ) , 
537-         warningTitle , 
538-         warningDescription , 
539-       ) ; 
532+     if  ( isSection2Locked )  { 
533+       this . createTransitionWarning ( sections . trainrunSection2 ,  node ) ; 
540534    } 
541535
542536    TransitionValidator . validateTransition ( node ,  transitionId ) ; 
543537    this . transitionsUpdated ( ) ; 
544538    this . nodesUpdated ( ) ; 
545539    this . operation . emit ( 
546-       new  TrainrunOperation ( OperationType . update ,  trainrunSections . trainrunSection1 . getTrainrun ( ) ) , 
540+       new  TrainrunOperation ( OperationType . update ,  sections . trainrunSection1 . getTrainrun ( ) ) , 
547541    ) ; 
548542  } 
549543
544+   toggleNonStop ( nodeId : number ,  transitionId : number )  { 
545+     const  node  =  this . getNodeFromId ( nodeId ) ; 
546+     node . toggleNonStop ( transitionId ) ; 
547+     this . propagateTimes ( nodeId ,  transitionId ,  true ) ; 
548+   } 
549+ 
550550  checkExistsNoCycleTrainrunAfterFreePortsConnecting ( 
551551    node : Node , 
552552    port1 : Port , 
@@ -1176,4 +1176,15 @@ export class NodeService implements OnDestroy {
11761176    } ) ; 
11771177    return  labelIDCauntMap ; 
11781178  } 
1179+ 
1180+   private  createTransitionWarning ( trainrunSection : TrainrunSection ,  node : Node )  { 
1181+     const  warningTitle  =  $localize `:@@app.services.data.node.transit-modified.title:Transition changed` ; 
1182+     const  warningDescription  =  $localize `:@@app.services.data.node.transit-modified.description:Times cannot be adjusted, the departure time is locked.` ; 
1183+     this . trainrunSectionService . setWarningOnNode ( 
1184+       trainrunSection . getId ( ) , 
1185+       node . getId ( ) , 
1186+       warningTitle , 
1187+       warningDescription , 
1188+     ) ; 
1189+   } 
11791190} 
0 commit comments