Sequential timelines

Hello,

I have a form with a few pages that can be accessed either linearly with the square buttons or randomly with the small bullets.
Each page has its timeline that moves them into and out of the scene.
It is working fine but the transitions of the pages are simultaneous and I want them to be sequential, the first page moving out and only then the second page moving in.
Is it possible?

Thanks

Form.hype.zip (135.5 KB)

I glanced at your document and it looks like:

  • you have timelines that move items into view
  • when a random-access button is pressed, you run that page's timeline to move things into view run every other page's timeline in reverse to move them out (so it doesn't matter which page is shown as all will definitely be removed)
  • Linear buttons are included in each page's elements, and are setup to specifically just to run the correct timelines (one forward for the next page, one reverse to move out the current page)

The one thing I wasn't certain about is that you have timeline actions that do a pause and also another timeline action that jumps back and plays in reverse. I didn't see how/went that might be used.


The easiest non-code solution would probably be to have each timeline's animations (and I guess timeline actions) move up by the transition time:

This would mean that the page out transition would happen immediately like before, as the timelines are at the end. And the while the page in transition would technically start immediately, nothing would animate until the page out had a chance to finish.


The easiest code solution I can think of is effectively doing the same thing, but just delays kicking off the starting of the page in timelines. So instead of a timeline action that continues those, you'd have a timeline action set to Run JavaScript… with code like:

window.setTimeout(function() {
   hypeDocument.continueTimelineNamed('Q4P3', hypeDocument.kDirectionForward, true);
}, ((8 / 30) * 1000)); // 8 frames in 30fps times 1000 milliseconds = ~267


However if the timeline actions come into more play with the timing for the fade out you'll need a bit more code. I'd probably add code that looks at all relevant timelines, and determines which is the longest. Then delay the page-in timeline until that amount.


There's probably other solutions you could use that can reduce code/timelines, though this would be a bit or reworking. For example, if you could probably make use of marking buttons with IDs or additional HTML data attributes, and use those for a script to gain knowledge on what to do. It could know which timelines to use, or possibly even use relative timelines to have a single timeline that moves things out.

Hopefully that at least gives some ideas! I don't think there's one true solution, and a lot depends on how much by way of changes you want to make as well as any future plans for your document. There's probably other ideas out there too :slight_smile:.

2 Likes

Hi Jonathan
Thank you for your ideas, I will use the timeout function, it is probably the solution I need.

The action that jump back and plays in reverse allows me to have a toggle button with only one Continue timeline action. If the time is at zero the timeline will run until the pause and if it is at pause time it will run a frame, jump back and return to zero.
I believe it was Hans-Gerd Claßen that first showed me this arrangement. It is a very simple and compact way to create a toggle button.

1 Like

The setTimeout function worked perfectly, I just changed it from 8/30 to 20/30 because the transition of the elements is 15 frames long.

Thank you very much!

1 Like

I was working on this any way .. seems great mind think alike... :smiley:

I was going to say it is easier to do this in code to control when the time line run and the buttons.
But I think @Jonathan probably just said that above ( not read it yet, sorry Jonathan )

Any way, I removed all the hidden buttons and made all the visible ones fire the same Hype function.

Each button including the arrows use a data attribute to say which time line we want.
The arrows though have the same data attribute but the value here is their actual name 'P0Volta', 'P0Vai'

The function is commented on how it works. But it determines if a round button was clicked or an arrow and works from there. It uses timeouts to delay the lowering of the info element, which should give enough time for any of the other to fully raise.

Form_mhv1.hype.zip (139.5 KB)

--

The code

	
	//== Set up current timeline counter
		 if (typeof hypeDocument.customData.currentTimeline == 'undefined'){
		 hypeDocument.customData.currentTimeline = 0
		 }
		 
			//== Set up  t timeline name array
	 hypeDocument.customData.element_timelines = ['Q4P1','Q4P2','Q4P3','Q4P4','Q4P5','Q4P6' ] 
	
		//== get the buttons timeline start name
	 	var thisEl_Timeline = element.dataset.timelinename
	
	
	//== Check if we are usng arrows and if we are already at the first or last index
	//== if we are then dont do anything
	
	if (thisEl_Timeline == 'P0Volta' ){
			 	if ( hypeDocument.customData.currentTimeline ==0)  {
			 	  return
			 	}
			} else if (thisEl_Timeline == 'P0Vai' ){
			
			
			if ( hypeDocument.customData.currentTimeline == hypeDocument.customData.element_timelines.length -1)  {
			 	  return
			 	}
			}
	
 	

for (let i = 0; i <  hypeDocument.customData.element_timelines.length; i++) { 
  
  //== loop over all time lines and close them
    hypeDocument.continueTimelineNamed( hypeDocument.customData.element_timelines[i], hypeDocument.kDirectionReverse, false) 
  
   
	 
		
	 if ( i + 1 ==  hypeDocument.customData.element_timelines.length ){
	 
	   // onces we have reached the last timeline in the array we check if we are a button or arrow
	   
	 	if (thisEl_Timeline == 'P0Volta' ||thisEl_Timeline == 'P0Vai' ){
	  		
	  		// we are a arrow - go to the arrows function 
			arrows()
			 
		} else {
			// we are a button - go to the buttons function 
			bttns(thisEl_Timeline)
	
		}
	 
	
	 }
}


 function bttns(thisEl_Timeline){

   setTimeout(function () {
   //== after timeout delay start the correct timelin to show
          for (let i = 0; i <  hypeDocument.customData.element_timelines.length; i++) { 
   
  			if ( hypeDocument.customData.element_timelines[i] == thisEl_Timeline){
	
	 		 
	 		 //== run timeline
	 		 hypeDocument.continueTimelineNamed( hypeDocument.customData.element_timelines[i], 		hypeDocument.kDirectionForward, true)
	 		 
	 		 hypeDocument.customData.currentTimeline = i 
			}
		} 
             }, 500);
 }
 
function arrows(){
 
  setTimeout(function () {
   //== after timeout delay start the correct timelin to show
   
   //== check which arrow
 if (thisEl_Timeline == 'P0Volta' ){
 
 	if ( hypeDocument.customData.currentTimeline >0)  {
 	//== increase currentTimeline number if are not going to go out of bounds of the array count
 	   hypeDocument.customData.currentTimeline -=  1
 	   }hypeDocument.continueTimelineNamed( hypeDocument.customData.element_timelines[hypeDocument.customData.currentTimeline ], hypeDocument.kDirectionForward, true)
	 		 
	 		 
			} else if (thisEl_Timeline == 'P0Vai'  ) {
			
			
			//== decrease currentTimeline number if are not going to go out of bounds of the array count
			if ( hypeDocument.customData.currentTimeline < hypeDocument.customData.element_timelines.length -1){
		 	hypeDocument.customData.currentTimeline +=  1	
		 	}
		 	
		 	
		 		 //== run  timeline
		 		 hypeDocument.continueTimelineNamed( hypeDocument.customData.element_timelines[hypeDocument.customData.currentTimeline  ], hypeDocument.kDirectionForward, true)
		  
		 
		  
		  }
 			
 }, 500);
 
}
2 Likes

It is fantastic Mark, very nice and clean!
Much better solution.

Thank you very much!

3 Likes