resolve notes merge conflict
						commit
						8582c9aac8
					
				
							
								
								
									
										23
									
								
								index.html
								
								
								
								
							
							
						
						
									
										23
									
								
								index.html
								
								
								
								
							|  | @ -24,8 +24,23 @@ | |||
| 	<body> | ||||
| 		<div class="reveal"> | ||||
| 			<div class="slides"> | ||||
| 				<section>Slide 1</section> | ||||
| 				<section>Slide 2</section> | ||||
| 				<section data-timing="6"> | ||||
| 					Slide 1 | ||||
| 
 | ||||
| 					<aside> | ||||
| 						these are not notes | ||||
| 					</aside> | ||||
| 					<aside class="notes"> | ||||
| 						these are notes for the first slide | ||||
| 					</aside> | ||||
| 				</section> | ||||
| 				<section> | ||||
| 					Slide 2 | ||||
| 
 | ||||
| 					<aside class="notes"> | ||||
| 						these are the nodes for the second slide | ||||
| 					</aside> | ||||
| 				</section> | ||||
| 			</div> | ||||
| 		</div> | ||||
| 
 | ||||
|  | @ -42,7 +57,9 @@ | |||
| 					{ src: 'plugin/markdown/markdown.js' }, | ||||
| 					{ src: 'plugin/notes/notes.js', async: true }, | ||||
| 					{ src: 'plugin/highlight/highlight.js', async: true, callback: function() { hljs.initHighlightingOnLoad(); } } | ||||
| 				] | ||||
| 				], | ||||
| 				controlsTutorial: false, | ||||
| 				defaultTiming: 3 | ||||
| 			}); | ||||
| 		</script> | ||||
| 	</body> | ||||
|  |  | |||
							
								
								
									
										21
									
								
								js/reveal.js
								
								
								
								
							
							
						
						
									
										21
									
								
								js/reveal.js
								
								
								
								
							|  | @ -4098,6 +4098,23 @@ | |||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| 	/** | ||||
| 	 * Returns an array of objects where each object represents the attributes on its respective slide. | ||||
| 	 */ | ||||
| 	function getSlidesMetaInfo() { | ||||
| 
 | ||||
| 		var slides = getSlides(); | ||||
| 		return slides.map( function (slide) { | ||||
| 			var meta = {}; | ||||
| 			for( var i = 0; i < slide.attributes.length; i++ ) { | ||||
| 				var attribute = slide.attributes[ i ]; | ||||
| 				meta[ attribute.name ] = attribute.value; | ||||
| 			} | ||||
| 			return meta; | ||||
| 		} ); | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| 	/** | ||||
| 	 * Retrieves the total number of slides in this presentation. | ||||
| 	 * | ||||
|  | @ -5454,6 +5471,10 @@ | |||
| 		// Returns an Array of all slides
 | ||||
| 		getSlides: getSlides, | ||||
| 
 | ||||
| 		// Returns an Array of objects representing the attributes on
 | ||||
| 		// the slides
 | ||||
| 		getSlidesMetaInfo: getSlidesMetaInfo, | ||||
| 
 | ||||
| 		// Returns the total number of slides
 | ||||
| 		getTotalSlides: getTotalSlides, | ||||
| 
 | ||||
|  |  | |||
|  | @ -347,6 +347,8 @@ | |||
| 					upcomingSlide, | ||||
| 					layoutLabel, | ||||
| 					layoutDropdown, | ||||
| 					pendingCalls = {}, | ||||
| 					lastRevealApiCallId = 0, | ||||
| 					connected = false; | ||||
| 
 | ||||
| 				var SPEAKER_LAYOUTS = { | ||||
|  | @ -382,6 +384,10 @@ | |||
| 						else if( data.type === 'state' ) { | ||||
| 							handleStateMessage( data ); | ||||
| 						} | ||||
| 						else if( data.type === 'return' ) { | ||||
| 							pendingCalls[data.callId](data.result); | ||||
| 							delete pendingCalls[data.callId]; | ||||
| 						} | ||||
| 					} | ||||
| 					// Messages sent by the reveal.js inside of the current slide preview | ||||
| 					else if( data && data.namespace === 'reveal' ) { | ||||
|  | @ -398,6 +404,21 @@ | |||
| 
 | ||||
| 				} ); | ||||
| 
 | ||||
| 				/** | ||||
| 				 * Asynchronously calls the Reveal.js API of the main frame. | ||||
| 				 */ | ||||
| 				function callRevealApi( methodName, methodArguments, callback ) { | ||||
| 					var callId = ++lastRevealApiCallId; | ||||
| 					pendingCalls[callId] = callback; | ||||
| 					window.opener.postMessage( JSON.stringify( { | ||||
| 						namespace: 'reveal-notes', | ||||
| 						type: 'call', | ||||
| 						callId: callId, | ||||
| 						methodName: methodName, | ||||
| 						arguments: methodArguments | ||||
| 					} ), '*' ); | ||||
| 				} | ||||
| 
 | ||||
| 				/** | ||||
| 				 * Called when the main window is trying to establish a | ||||
| 				 * connection. | ||||
|  | @ -512,28 +533,34 @@ | |||
| 
 | ||||
| 				} | ||||
| 
 | ||||
| 				function getTimings() { | ||||
| 				function getTimings( callback ) { | ||||
| 
 | ||||
| 					var slides = Reveal.getSlides(); | ||||
| 					var defaultTiming = Reveal.getConfig().defaultTiming; | ||||
| 					if (defaultTiming == null) { | ||||
| 						return null; | ||||
| 					} | ||||
| 					var timings = []; | ||||
| 					for ( var i in slides ) { | ||||
| 						var slide = slides[i]; | ||||
| 						var timing = defaultTiming; | ||||
| 						if( slide.hasAttribute( 'data-timing' )) { | ||||
| 							var t = slide.getAttribute( 'data-timing' ); | ||||
| 							timing = parseInt(t); | ||||
| 							if( isNaN(timing) ) { | ||||
| 								console.warn("Could not parse timing '" + t + "' of slide " + i + "; using default of " + defaultTiming); | ||||
| 								timing = defaultTiming; | ||||
| 					callRevealApi( 'getSlidesMetaInfo', [], function ( slides ) { | ||||
| 						callRevealApi( 'getConfig', [], function ( config ) { | ||||
| 							var defaultTiming = config.defaultTiming; | ||||
| 							if (defaultTiming == null) { | ||||
| 								callback(null); | ||||
| 								return; | ||||
| 							} | ||||
| 						} | ||||
| 						timings.push(timing); | ||||
| 					} | ||||
| 					return timings; | ||||
| 
 | ||||
| 							var timings = []; | ||||
| 							for ( var i in slides ) { | ||||
| 								var slide = slides[ i ]; | ||||
| 								var timing = defaultTiming; | ||||
| 								if( slide.hasOwnProperty( 'data-timing' )) { | ||||
| 									var t = slide[ 'data-timing' ]; | ||||
| 									timing = parseInt(t); | ||||
| 									if( isNaN(timing) ) { | ||||
| 										console.warn("Could not parse timing '" + t + "' of slide " + i + "; using default of " + defaultTiming); | ||||
| 										timing = defaultTiming; | ||||
| 									} | ||||
| 								} | ||||
| 								timings.push(timing); | ||||
| 							} | ||||
| 
 | ||||
| 							callback( timings ); | ||||
| 						} ); | ||||
| 					} ); | ||||
| 
 | ||||
| 				} | ||||
| 
 | ||||
|  | @ -541,15 +568,15 @@ | |||
| 				 * Return the number of seconds allocated for presenting | ||||
| 				 * all slides up to and including this one. | ||||
| 				 */ | ||||
| 				function getTimeAllocated(timings) { | ||||
| 				function getTimeAllocated( timings, callback ) { | ||||
| 
 | ||||
| 					var slides = Reveal.getSlides(); | ||||
| 					var allocated = 0; | ||||
| 					var currentSlide = Reveal.getSlidePastCount(); | ||||
| 					for (var i in slides.slice(0, currentSlide + 1)) { | ||||
| 						allocated += timings[i]; | ||||
| 					} | ||||
| 					return allocated; | ||||
| 					callRevealApi( 'getSlidePastCount', [], function ( currentSlide ) { | ||||
| 						var allocated = 0; | ||||
| 						for (var i in timings.slice(0, currentSlide + 1)) { | ||||
| 							allocated += timings[i]; | ||||
| 						} | ||||
| 						callback( allocated ); | ||||
| 					} ); | ||||
| 
 | ||||
| 				} | ||||
| 
 | ||||
|  | @ -571,12 +598,51 @@ | |||
| 					pacingMinutesEl = pacingEl.querySelector( '.minutes-value' ), | ||||
| 					pacingSecondsEl = pacingEl.querySelector( '.seconds-value' ); | ||||
| 
 | ||||
| 					var timings = getTimings(); | ||||
| 					if (timings !== null) { | ||||
| 						pacingTitleEl.style.removeProperty('display'); | ||||
| 						pacingEl.style.removeProperty('display'); | ||||
| 					var timings = null; | ||||
| 					getTimings( function ( _timings ) { | ||||
| 
 | ||||
| 						timings = _timings; | ||||
| 						if (_timings !== null) { | ||||
| 							pacingTitleEl.style.removeProperty('display'); | ||||
| 							pacingEl.style.removeProperty('display'); | ||||
| 						} | ||||
| 
 | ||||
| 						// Update once directly | ||||
| 						_updateTimer(); | ||||
| 
 | ||||
| 						// Then update every second | ||||
| 						setInterval( _updateTimer, 1000 ); | ||||
| 
 | ||||
| 					} ); | ||||
| 
 | ||||
| 
 | ||||
| 					function _resetTimer() { | ||||
| 
 | ||||
| 						if (timings == null) { | ||||
| 							start = new Date(); | ||||
| 							_updateTimer(); | ||||
| 						} | ||||
| 						else { | ||||
| 							// Reset timer to beginning of current slide | ||||
| 							getTimeAllocated( timings, function ( slideEndTimingSeconds ) { | ||||
| 								var slideEndTiming = slideEndTimingSeconds * 1000; | ||||
| 								callRevealApi( 'getSlidePastCount', [], function ( currentSlide ) { | ||||
| 									var currentSlideTiming = timings[currentSlide] * 1000; | ||||
| 									var previousSlidesTiming = slideEndTiming - currentSlideTiming; | ||||
| 									var now = new Date(); | ||||
| 									start = new Date(now.getTime() - previousSlidesTiming); | ||||
| 									_updateTimer(); | ||||
| 								} ); | ||||
| 							} ); | ||||
| 						} | ||||
| 
 | ||||
| 					} | ||||
| 
 | ||||
| 					timeEl.addEventListener( 'click', function() { | ||||
| 						_resetTimer(); | ||||
| 						return false; | ||||
| 					} ); | ||||
| 
 | ||||
| 					function _displayTime( hrEl, minEl, secEl, time) { | ||||
| 
 | ||||
| 						var sign = Math.sign(time) == -1 ? "-" : ""; | ||||
|  | @ -618,52 +684,26 @@ | |||
| 
 | ||||
| 					function _updatePacing(diff) { | ||||
| 
 | ||||
| 						var slideEndTiming = getTimeAllocated(timings) * 1000; | ||||
| 						var currentSlide = Reveal.getSlidePastCount(); | ||||
| 						var currentSlideTiming = timings[currentSlide] * 1000; | ||||
| 						var timeLeftCurrentSlide = slideEndTiming - diff; | ||||
| 						if (timeLeftCurrentSlide < 0) { | ||||
| 							pacingEl.className = 'pacing behind'; | ||||
| 						} | ||||
| 						else if (timeLeftCurrentSlide < currentSlideTiming) { | ||||
| 							pacingEl.className = 'pacing on-track'; | ||||
| 						} | ||||
| 						else { | ||||
| 							pacingEl.className = 'pacing ahead'; | ||||
| 						} | ||||
| 						_displayTime( pacingHoursEl, pacingMinutesEl, pacingSecondsEl, timeLeftCurrentSlide ); | ||||
| 						getTimeAllocated( timings, function ( slideEndTimingSeconds ) { | ||||
| 							var slideEndTiming = slideEndTimingSeconds * 1000; | ||||
| 
 | ||||
| 							callRevealApi( 'getSlidePastCount', [], function ( currentSlide ) { | ||||
| 								var currentSlideTiming = timings[currentSlide] * 1000; | ||||
| 								var timeLeftCurrentSlide = slideEndTiming - diff; | ||||
| 								if (timeLeftCurrentSlide < 0) { | ||||
| 									pacingEl.className = 'pacing behind'; | ||||
| 								} | ||||
| 								else if (timeLeftCurrentSlide < currentSlideTiming) { | ||||
| 									pacingEl.className = 'pacing on-track'; | ||||
| 								} | ||||
| 								else { | ||||
| 									pacingEl.className = 'pacing ahead'; | ||||
| 								} | ||||
| 								_displayTime( pacingHoursEl, pacingMinutesEl, pacingSecondsEl, timeLeftCurrentSlide ); | ||||
| 							} ); | ||||
| 						} ); | ||||
| 					} | ||||
| 
 | ||||
| 					// Update once directly | ||||
| 					_updateTimer(); | ||||
| 
 | ||||
| 					// Then update every second | ||||
| 					setInterval( _updateTimer, 1000 ); | ||||
| 
 | ||||
| 					function _resetTimer() { | ||||
| 
 | ||||
| 						if (timings == null) { | ||||
| 							start = new Date(); | ||||
| 						} | ||||
| 						else { | ||||
| 							// Reset timer to beginning of current slide | ||||
| 							var slideEndTiming = getTimeAllocated(timings) * 1000; | ||||
| 							var currentSlide = Reveal.getSlidePastCount(); | ||||
| 							var currentSlideTiming = timings[currentSlide] * 1000; | ||||
| 							var previousSlidesTiming = slideEndTiming - currentSlideTiming; | ||||
| 							var now = new Date(); | ||||
| 							start = new Date(now.getTime() - previousSlidesTiming); | ||||
| 						} | ||||
| 						_updateTimer(); | ||||
| 
 | ||||
| 					} | ||||
| 
 | ||||
| 					timeEl.addEventListener( 'click', function() { | ||||
| 						_resetTimer(); | ||||
| 						return false; | ||||
| 					} ); | ||||
| 
 | ||||
| 				} | ||||
| 
 | ||||
| 				/** | ||||
|  |  | |||
|  | @ -26,9 +26,6 @@ var RevealNotes = (function() { | |||
| 			return; | ||||
| 		} | ||||
| 
 | ||||
| 		// Allow popup window access to Reveal API
 | ||||
| 		notesPopup.Reveal = window.Reveal; | ||||
| 
 | ||||
| 		/** | ||||
| 		 * Connect to the notes window through a postmessage handshake. | ||||
| 		 * Using postmessage enables us to work in situations where the | ||||
|  | @ -52,9 +49,26 @@ var RevealNotes = (function() { | |||
| 					clearInterval( connectInterval ); | ||||
| 					onConnected(); | ||||
| 				} | ||||
| 				if( data && data.namespace === 'reveal-notes' && data.type === 'call' ) { | ||||
| 					callRevealApi( data.methodName, data.arguments, data.callId ); | ||||
| 				} | ||||
| 			} ); | ||||
| 		} | ||||
| 
 | ||||
| 		/** | ||||
| 		 * Calls the specified Reveal.js method with the provided argument and then pushes the result to the notes | ||||
| 		 * frame. | ||||
| 		 */ | ||||
| 		function callRevealApi( methodName, methodArguments, callId ) { | ||||
| 			var result = Reveal[methodName].call(Reveal, methodArguments); | ||||
| 			notesPopup.postMessage( JSON.stringify( { | ||||
| 				namespace: 'reveal-notes', | ||||
| 				type: 'return', | ||||
| 				result: result, | ||||
| 				callId: callId | ||||
| 			} ), '*' ); | ||||
| 		} | ||||
| 
 | ||||
| 		/** | ||||
| 		 * Posts the current slide data to the notes window | ||||
| 		 */ | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue
	
	 Hakim El Hattab
						Hakim El Hattab