Merge branch 'dev' into plugin-markdown
commit
03126c509e
|
@ -25,4 +25,4 @@ Want to create your presentation using a visual editor? Try the official reveal.
|
|||
|
||||
MIT licensed
|
||||
|
||||
Copyright (C) 2011-2020 Hakim El Hattab, https://hakim.se
|
||||
Copyright (C) 2011-2021 Hakim El Hattab, https://hakim.se
|
||||
|
|
|
@ -1158,54 +1158,54 @@ $controlsArrowAngleActive: 36deg;
|
|||
}
|
||||
|
||||
/* Immediate transition style */
|
||||
.reveal[data-background-transition=none]>.backgrounds .slide-background,
|
||||
.reveal[data-background-transition=none]>.backgrounds .slide-background:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background[data-background-transition=none] {
|
||||
transition: none;
|
||||
}
|
||||
|
||||
/* Slide */
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background,
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background[data-background-transition=slide] {
|
||||
opacity: 1;
|
||||
backface-visibility: hidden;
|
||||
}
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background.past,
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.past[data-background-transition=slide] {
|
||||
transform: translate(-100%, 0);
|
||||
}
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background.future,
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.future[data-background-transition=slide] {
|
||||
transform: translate(100%, 0);
|
||||
}
|
||||
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background>.slide-background.past,
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background>.slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.past[data-background-transition=slide] {
|
||||
transform: translate(0, -100%);
|
||||
}
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background>.slide-background.future,
|
||||
.reveal[data-background-transition=slide]>.backgrounds .slide-background>.slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.future[data-background-transition=slide] {
|
||||
transform: translate(0, 100%);
|
||||
}
|
||||
|
||||
|
||||
/* Convex */
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background.past,
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.past[data-background-transition=convex] {
|
||||
opacity: 0;
|
||||
transform: translate3d(-100%, 0, 0) rotateY(-90deg) translate3d(-100%, 0, 0);
|
||||
}
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background.future,
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.future[data-background-transition=convex] {
|
||||
opacity: 0;
|
||||
transform: translate3d(100%, 0, 0) rotateY(90deg) translate3d(100%, 0, 0);
|
||||
}
|
||||
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background>.slide-background.past,
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background>.slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.past[data-background-transition=convex] {
|
||||
opacity: 0;
|
||||
transform: translate3d(0, -100%, 0) rotateX(90deg) translate3d(0, -100%, 0);
|
||||
}
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background>.slide-background.future,
|
||||
.reveal[data-background-transition=convex]>.backgrounds .slide-background>.slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.future[data-background-transition=convex] {
|
||||
opacity: 0;
|
||||
transform: translate3d(0, 100%, 0) rotateX(-90deg) translate3d(0, 100%, 0);
|
||||
|
@ -1213,54 +1213,54 @@ $controlsArrowAngleActive: 36deg;
|
|||
|
||||
|
||||
/* Concave */
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background.past,
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.past[data-background-transition=concave] {
|
||||
opacity: 0;
|
||||
transform: translate3d(-100%, 0, 0) rotateY(90deg) translate3d(-100%, 0, 0);
|
||||
}
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background.future,
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.future[data-background-transition=concave] {
|
||||
opacity: 0;
|
||||
transform: translate3d(100%, 0, 0) rotateY(-90deg) translate3d(100%, 0, 0);
|
||||
}
|
||||
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background>.slide-background.past,
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background>.slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.past[data-background-transition=concave] {
|
||||
opacity: 0;
|
||||
transform: translate3d(0, -100%, 0) rotateX(-90deg) translate3d(0, -100%, 0);
|
||||
}
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background>.slide-background.future,
|
||||
.reveal[data-background-transition=concave]>.backgrounds .slide-background>.slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.future[data-background-transition=concave] {
|
||||
opacity: 0;
|
||||
transform: translate3d(0, 100%, 0) rotateX(90deg) translate3d(0, 100%, 0);
|
||||
}
|
||||
|
||||
/* Zoom */
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background,
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background[data-background-transition=zoom] {
|
||||
transition-timing-function: ease;
|
||||
}
|
||||
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background.past,
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.past[data-background-transition=zoom] {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
transform: scale(16);
|
||||
}
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background.future,
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background.future[data-background-transition=zoom] {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
transform: scale(0.2);
|
||||
}
|
||||
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background>.slide-background.past,
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background>.slide-background.past:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.past[data-background-transition=zoom] {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
transform: scale(16);
|
||||
}
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background>.slide-background.future,
|
||||
.reveal[data-background-transition=zoom]>.backgrounds .slide-background>.slide-background.future:not([data-background-transition]),
|
||||
.reveal>.backgrounds .slide-background>.slide-background.future[data-background-transition=zoom] {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
|
|
|
@ -185,6 +185,7 @@
|
|||
.reveal code {
|
||||
font-family: $codeFont;
|
||||
text-transform: none;
|
||||
tab-size: 2;
|
||||
}
|
||||
|
||||
.reveal pre code {
|
||||
|
|
26
demo.html
26
demo.html
|
@ -19,7 +19,7 @@
|
|||
<link rel="stylesheet" href="dist/theme/black.css" id="theme">
|
||||
|
||||
<!-- Theme used for syntax highlighting of code -->
|
||||
<link rel="stylesheet" href="plugin/highlight/monokai.css" id="highlight-theme">
|
||||
<link rel="stylesheet" href="plugin/highlight/monokai.css">
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
@ -186,7 +186,7 @@
|
|||
Write content using inline or external Markdown.
|
||||
Instructions and more info available in the [docs](https://revealjs.com/markdown/).
|
||||
|
||||
```[]
|
||||
```html []
|
||||
<section data-markdown>
|
||||
## Markdown support
|
||||
|
||||
|
@ -249,17 +249,17 @@
|
|||
<p>
|
||||
reveal.js comes with a few themes built in: <br>
|
||||
<!-- Hacks to swap themes after the page has loaded. Not flexible and only intended for the reveal.js demo deck. -->
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/black.css'); return false;">Black (default)</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/white.css'); return false;">White</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/league.css'); return false;">League</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/sky.css'); return false;">Sky</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/beige.css'); return false;">Beige</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/simple.css'); return false;">Simple</a> <br>
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/serif.css'); return false;">Serif</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/blood.css'); return false;">Blood</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/night.css'); return false;">Night</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/moon.css'); return false;">Moon</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','css/theme/solarized.css'); return false;">Solarized</a>
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/black.css'); return false;">Black (default)</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/white.css'); return false;">White</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/league.css'); return false;">League</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/sky.css'); return false;">Sky</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/beige.css'); return false;">Beige</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/simple.css'); return false;">Simple</a> <br>
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/serif.css'); return false;">Serif</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/blood.css'); return false;">Blood</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/night.css'); return false;">Night</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/moon.css'); return false;">Moon</a> -
|
||||
<a href="#" onclick="document.getElementById('theme').setAttribute('href','dist/theme/solarized.css'); return false;">Solarized</a>
|
||||
</p>
|
||||
</section>
|
||||
|
||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -194,7 +194,8 @@ section.has-dark-background, section.has-dark-background h1, section.has-dark-ba
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -187,7 +187,8 @@ section.has-light-background, section.has-light-background h1, section.has-light
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -193,7 +193,8 @@ section.has-light-background, section.has-light-background h1, section.has-light
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -196,7 +196,8 @@ section.has-light-background, section.has-light-background h1, section.has-light
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -194,7 +194,8 @@ section.has-light-background, section.has-light-background h1, section.has-light
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -188,7 +188,8 @@ section.has-light-background, section.has-light-background h1, section.has-light
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -190,7 +190,8 @@ section.has-dark-background, section.has-dark-background h1, section.has-dark-ba
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -190,7 +190,8 @@ section.has-dark-background, section.has-dark-background h1, section.has-dark-ba
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -197,7 +197,8 @@ section.has-dark-background, section.has-dark-background h1, section.has-dark-ba
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -191,7 +191,8 @@ html * {
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -187,7 +187,8 @@ section.has-dark-background, section.has-dark-background h1, section.has-dark-ba
|
|||
|
||||
.reveal code {
|
||||
font-family: monospace;
|
||||
text-transform: none; }
|
||||
text-transform: none;
|
||||
tab-size: 2; }
|
||||
|
||||
.reveal pre code {
|
||||
display: block;
|
||||
|
|
|
@ -32,6 +32,8 @@ const banner = `/*!
|
|||
* Copyright (C) 2020 Hakim El Hattab, https://hakim.se
|
||||
*/\n`
|
||||
|
||||
sass.compiler = require('node-sass');
|
||||
|
||||
// Prevents warnings from opening too many test pages
|
||||
process.setMaxListeners(20);
|
||||
|
||||
|
|
|
@ -8,10 +8,10 @@
|
|||
|
||||
<link rel="stylesheet" href="dist/reset.css">
|
||||
<link rel="stylesheet" href="dist/reveal.css">
|
||||
<link rel="stylesheet" href="dist/theme/black.css" id="theme">
|
||||
<link rel="stylesheet" href="dist/theme/black.css">
|
||||
|
||||
<!-- Theme used for syntax highlighted code -->
|
||||
<link rel="stylesheet" href="plugin/highlight/monokai.css" id="highlight-theme">
|
||||
<link rel="stylesheet" href="plugin/highlight/monokai.css">
|
||||
</head>
|
||||
<body>
|
||||
<div class="reveal">
|
||||
|
|
|
@ -73,8 +73,8 @@ export default {
|
|||
|
||||
// Optional function that blocks keyboard events when retuning false
|
||||
//
|
||||
// If you set this to 'foucsed', we will only capture keyboard events
|
||||
// for embdedded decks when they are in focus
|
||||
// If you set this to 'focused', we will only capture keyboard events
|
||||
// for embedded decks when they are in focus
|
||||
keyboardCondition: null,
|
||||
|
||||
// Disables the default reveal.js slide layout (scaling and centering)
|
||||
|
@ -149,7 +149,7 @@ export default {
|
|||
// Flags if slides with data-visibility="hidden" should be kep visible
|
||||
showHiddenSlides: false,
|
||||
|
||||
// Global override for autolaying embedded media (video/audio/iframe)
|
||||
// Global override for autoplaying embedded media (video/audio/iframe)
|
||||
// - null: Media will only autoplay if data-autoplay is present
|
||||
// - true: All media will autoplay, regardless of individual setting
|
||||
// - false: No media will autoplay, regardless of individual setting
|
||||
|
|
|
@ -27,8 +27,6 @@ export default class Backgrounds {
|
|||
*/
|
||||
create() {
|
||||
|
||||
let printMode = this.Reveal.isPrintingPDF();
|
||||
|
||||
// Clear prior backgrounds
|
||||
this.element.innerHTML = '';
|
||||
this.element.classList.add( 'no-transition' );
|
||||
|
@ -114,9 +112,24 @@ export default class Backgrounds {
|
|||
*/
|
||||
sync( slide ) {
|
||||
|
||||
let element = slide.slideBackgroundElement,
|
||||
const element = slide.slideBackgroundElement,
|
||||
contentElement = slide.slideBackgroundContentElement;
|
||||
|
||||
const data = {
|
||||
background: slide.getAttribute( 'data-background' ),
|
||||
backgroundSize: slide.getAttribute( 'data-background-size' ),
|
||||
backgroundImage: slide.getAttribute( 'data-background-image' ),
|
||||
backgroundVideo: slide.getAttribute( 'data-background-video' ),
|
||||
backgroundIframe: slide.getAttribute( 'data-background-iframe' ),
|
||||
backgroundColor: slide.getAttribute( 'data-background-color' ),
|
||||
backgroundRepeat: slide.getAttribute( 'data-background-repeat' ),
|
||||
backgroundPosition: slide.getAttribute( 'data-background-position' ),
|
||||
backgroundTransition: slide.getAttribute( 'data-background-transition' ),
|
||||
backgroundOpacity: slide.getAttribute( 'data-background-opacity' ),
|
||||
};
|
||||
|
||||
const dataPreload = slide.hasAttribute( 'data-preload' );
|
||||
|
||||
// Reset the prior background state in case this is not the
|
||||
// initial sync
|
||||
slide.classList.remove( 'has-dark-background' );
|
||||
|
@ -135,19 +148,6 @@ export default class Backgrounds {
|
|||
contentElement.style.opacity = '';
|
||||
contentElement.innerHTML = '';
|
||||
|
||||
let data = {
|
||||
background: slide.getAttribute( 'data-background' ),
|
||||
backgroundSize: slide.getAttribute( 'data-background-size' ),
|
||||
backgroundImage: slide.getAttribute( 'data-background-image' ),
|
||||
backgroundVideo: slide.getAttribute( 'data-background-video' ),
|
||||
backgroundIframe: slide.getAttribute( 'data-background-iframe' ),
|
||||
backgroundColor: slide.getAttribute( 'data-background-color' ),
|
||||
backgroundRepeat: slide.getAttribute( 'data-background-repeat' ),
|
||||
backgroundPosition: slide.getAttribute( 'data-background-position' ),
|
||||
backgroundTransition: slide.getAttribute( 'data-background-transition' ),
|
||||
backgroundOpacity: slide.getAttribute( 'data-background-opacity' )
|
||||
};
|
||||
|
||||
if( data.background ) {
|
||||
// Auto-wrap image urls in url(...)
|
||||
if( /^(http|file|\/\/)/gi.test( data.background ) || /\.(svg|png|jpg|jpeg|gif|bmp)([?#\s]|$)/gi.test( data.background ) ) {
|
||||
|
@ -179,7 +179,7 @@ export default class Backgrounds {
|
|||
if( data.backgroundColor ) element.style.backgroundColor = data.backgroundColor;
|
||||
if( data.backgroundTransition ) element.setAttribute( 'data-background-transition', data.backgroundTransition );
|
||||
|
||||
if( slide.hasAttribute( 'data-preload' ) ) element.setAttribute( 'data-preload', '' );
|
||||
if( dataPreload ) element.setAttribute( 'data-preload', '' );
|
||||
|
||||
// Background image options are set on the content wrapper
|
||||
if( data.backgroundSize ) contentElement.style.backgroundSize = data.backgroundSize;
|
||||
|
@ -192,8 +192,8 @@ export default class Backgrounds {
|
|||
// color, no class will be added
|
||||
let contrastColor = data.backgroundColor;
|
||||
|
||||
// If no bg color was found, check the computed background
|
||||
if( !contrastColor ) {
|
||||
// If no bg color was found, or it cannot be converted by colorToRgb, check the computed background
|
||||
if( !contrastColor || !colorToRgb( contrastColor ) ) {
|
||||
let computedBackgroundStyle = window.getComputedStyle( element );
|
||||
if( computedBackgroundStyle && computedBackgroundStyle.backgroundColor ) {
|
||||
contrastColor = computedBackgroundStyle.backgroundColor;
|
||||
|
@ -201,7 +201,7 @@ export default class Backgrounds {
|
|||
}
|
||||
|
||||
if( contrastColor ) {
|
||||
let rgb = colorToRgb( contrastColor );
|
||||
const rgb = colorToRgb( contrastColor );
|
||||
|
||||
// Ignore fully transparent backgrounds. Some browsers return
|
||||
// rgba(0,0,0,0) when reading the computed background color of
|
||||
|
|
|
@ -235,6 +235,7 @@ export default class Fragments {
|
|||
el.classList.remove( 'current-fragment' );
|
||||
|
||||
if( wasVisible ) {
|
||||
this.Reveal.slideContent.stopEmbeddedContent( el );
|
||||
changedFragments.hidden.push( el );
|
||||
this.Reveal.dispatchEvent({
|
||||
target: el,
|
||||
|
|
|
@ -16,20 +16,26 @@ export default class Print {
|
|||
* Configures the presentation for printing to a static
|
||||
* PDF.
|
||||
*/
|
||||
setupPDF() {
|
||||
async setupPDF() {
|
||||
|
||||
let config = this.Reveal.getConfig();
|
||||
const config = this.Reveal.getConfig();
|
||||
const slides = queryAll( this.Reveal.getRevealElement(), SLIDES_SELECTOR )
|
||||
|
||||
let slideSize = this.Reveal.getComputedSlideSize( window.innerWidth, window.innerHeight );
|
||||
// Compute slide numbers now, before we start duplicating slides
|
||||
const doingSlideNumbers = config.slideNumber && /all|print/i.test( config.showSlideNumber );
|
||||
|
||||
const slideSize = this.Reveal.getComputedSlideSize( window.innerWidth, window.innerHeight );
|
||||
|
||||
// Dimensions of the PDF pages
|
||||
let pageWidth = Math.floor( slideSize.width * ( 1 + config.margin ) ),
|
||||
const pageWidth = Math.floor( slideSize.width * ( 1 + config.margin ) ),
|
||||
pageHeight = Math.floor( slideSize.height * ( 1 + config.margin ) );
|
||||
|
||||
// Dimensions of slides within the pages
|
||||
let slideWidth = slideSize.width,
|
||||
const slideWidth = slideSize.width,
|
||||
slideHeight = slideSize.height;
|
||||
|
||||
await new Promise( requestAnimationFrame );
|
||||
|
||||
// Let the browser know what page size we want to print
|
||||
createStyleSheet( '@page{size:'+ pageWidth +'px '+ pageHeight +'px; margin: 0px;}' );
|
||||
|
||||
|
@ -41,25 +47,32 @@ export default class Print {
|
|||
document.body.style.height = pageHeight + 'px';
|
||||
|
||||
// Make sure stretch elements fit on slide
|
||||
await new Promise( requestAnimationFrame );
|
||||
this.Reveal.layoutSlideContents( slideWidth, slideHeight );
|
||||
|
||||
// Compute slide numbers now, before we start duplicating slides
|
||||
let doingSlideNumbers = config.slideNumber && /all|print/i.test( config.showSlideNumber );
|
||||
queryAll( this.Reveal.getRevealElement(), SLIDES_SELECTOR ).forEach( function( slide ) {
|
||||
slide.setAttribute( 'data-slide-number', this.Reveal.slideNumber.getSlideNumber( slide ) );
|
||||
}, this );
|
||||
// Re-run the slide layout so that r-fit-text is applied based on
|
||||
// the printed slide size
|
||||
slides.forEach( slide => this.Reveal.slideContent.layout( slide ) );
|
||||
|
||||
// Batch scrollHeight access to prevent layout thrashing
|
||||
await new Promise( requestAnimationFrame );
|
||||
|
||||
const slideScrollHeights = slides.map( slide => slide.scrollHeight );
|
||||
|
||||
const pages = [];
|
||||
const pageContainer = slides[0].parentNode;
|
||||
|
||||
// Slide and slide background layout
|
||||
queryAll( this.Reveal.getRevealElement(), SLIDES_SELECTOR ).forEach( function( slide ) {
|
||||
slides.forEach( function( slide, index ) {
|
||||
|
||||
// Vertical stacks are not centred since their section
|
||||
// children will be
|
||||
if( slide.classList.contains( 'stack' ) === false ) {
|
||||
// Center the slide inside of the page, giving the slide some margin
|
||||
let left = ( pageWidth - slideWidth ) / 2,
|
||||
top = ( pageHeight - slideHeight ) / 2;
|
||||
let left = ( pageWidth - slideWidth ) / 2;
|
||||
let top = ( pageHeight - slideHeight ) / 2;
|
||||
|
||||
let contentHeight = slide.scrollHeight;
|
||||
const contentHeight = slideScrollHeights[ index ];
|
||||
let numberOfPages = Math.max( Math.ceil( contentHeight / pageHeight ), 1 );
|
||||
|
||||
// Adhere to configured pages per slide limit
|
||||
|
@ -72,10 +85,11 @@ export default class Print {
|
|||
|
||||
// Wrap the slide in a page element and hide its overflow
|
||||
// so that no page ever flows onto another
|
||||
let page = document.createElement( 'div' );
|
||||
const page = document.createElement( 'div' );
|
||||
pages.push( page );
|
||||
|
||||
page.className = 'pdf-page';
|
||||
page.style.height = ( ( pageHeight + config.pdfPageHeightOffset ) * numberOfPages ) + 'px';
|
||||
slide.parentNode.insertBefore( page, slide );
|
||||
page.appendChild( slide );
|
||||
|
||||
// Position the slide inside of the page
|
||||
|
@ -91,19 +105,19 @@ export default class Print {
|
|||
if( config.showNotes ) {
|
||||
|
||||
// Are there notes for this slide?
|
||||
let notes = this.Reveal.getSlideNotes( slide );
|
||||
const notes = this.Reveal.getSlideNotes( slide );
|
||||
if( notes ) {
|
||||
|
||||
let notesSpacing = 8;
|
||||
let notesLayout = typeof config.showNotes === 'string' ? config.showNotes : 'inline';
|
||||
let notesElement = document.createElement( 'div' );
|
||||
const notesSpacing = 8;
|
||||
const notesLayout = typeof config.showNotes === 'string' ? config.showNotes : 'inline';
|
||||
const notesElement = document.createElement( 'div' );
|
||||
notesElement.classList.add( 'speaker-notes' );
|
||||
notesElement.classList.add( 'speaker-notes-pdf' );
|
||||
notesElement.setAttribute( 'data-layout', notesLayout );
|
||||
notesElement.innerHTML = notes;
|
||||
|
||||
if( notesLayout === 'separate-page' ) {
|
||||
page.parentNode.insertBefore( notesElement, page.nextSibling );
|
||||
pages.push( notesElement );
|
||||
}
|
||||
else {
|
||||
notesElement.style.left = notesSpacing + 'px';
|
||||
|
@ -118,10 +132,11 @@ export default class Print {
|
|||
|
||||
// Inject slide numbers if `slideNumbers` are enabled
|
||||
if( doingSlideNumbers ) {
|
||||
let numberElement = document.createElement( 'div' );
|
||||
const slideNumber = index + 1;
|
||||
const numberElement = document.createElement( 'div' );
|
||||
numberElement.classList.add( 'slide-number' );
|
||||
numberElement.classList.add( 'slide-number-pdf' );
|
||||
numberElement.innerHTML = slide.getAttribute( 'data-slide-number' );
|
||||
numberElement.innerHTML = slideNumber;
|
||||
page.appendChild( numberElement );
|
||||
}
|
||||
|
||||
|
@ -131,10 +146,9 @@ export default class Print {
|
|||
// Each fragment 'group' is an array containing one or more
|
||||
// fragments. Multiple fragments that appear at the same time
|
||||
// are part of the same group.
|
||||
let fragmentGroups = this.Reveal.fragments.sort( page.querySelectorAll( '.fragment' ), true );
|
||||
const fragmentGroups = this.Reveal.fragments.sort( page.querySelectorAll( '.fragment' ), true );
|
||||
|
||||
let previousFragmentStep;
|
||||
let previousPage;
|
||||
|
||||
fragmentGroups.forEach( function( fragments ) {
|
||||
|
||||
|
@ -151,11 +165,10 @@ export default class Print {
|
|||
}, this );
|
||||
|
||||
// Create a separate page for the current fragment state
|
||||
let clonedPage = page.cloneNode( true );
|
||||
page.parentNode.insertBefore( clonedPage, ( previousPage || page ).nextSibling );
|
||||
const clonedPage = page.cloneNode( true );
|
||||
pages.push( clonedPage );
|
||||
|
||||
previousFragmentStep = fragments;
|
||||
previousPage = clonedPage;
|
||||
|
||||
}, this );
|
||||
|
||||
|
@ -178,6 +191,10 @@ export default class Print {
|
|||
|
||||
}, this );
|
||||
|
||||
await new Promise( requestAnimationFrame );
|
||||
|
||||
pages.forEach( page => pageContainer.appendChild( page ) );
|
||||
|
||||
// Notify subscribers that the PDF layout is good to go
|
||||
this.Reveal.dispatchEvent({ type: 'pdf-ready' });
|
||||
|
||||
|
|
|
@ -88,14 +88,16 @@ export default class Progress {
|
|||
|
||||
event.preventDefault();
|
||||
|
||||
let slidesTotal = this.Reveal.getHorizontalSlides().length;
|
||||
let slides = this.Reveal.getSlides();
|
||||
let slidesTotal = slides.length;
|
||||
let slideIndex = Math.floor( ( event.clientX / this.getMaxWidth() ) * slidesTotal );
|
||||
|
||||
if( this.Reveal.getConfig().rtl ) {
|
||||
slideIndex = slidesTotal - slideIndex;
|
||||
}
|
||||
|
||||
this.Reveal.slide( slideIndex );
|
||||
let targetIndices = this.Reveal.getIndices(slides[slideIndex]);
|
||||
this.Reveal.slide( targetIndices.h, targetIndices.v );
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -102,7 +102,9 @@ export default class SlideContent {
|
|||
|
||||
// Images
|
||||
if( backgroundImage ) {
|
||||
backgroundContent.style.backgroundImage = 'url('+ encodeURI( backgroundImage ) +')';
|
||||
backgroundContent.style.backgroundImage = backgroundImage.split( ',' ).map( background => {
|
||||
return `url(${encodeURI(background.trim())})`;
|
||||
}).join( ',' );
|
||||
}
|
||||
// Videos
|
||||
else if ( backgroundVideo && !this.Reveal.isSpeakerNotes() ) {
|
||||
|
@ -167,11 +169,20 @@ export default class SlideContent {
|
|||
|
||||
}
|
||||
|
||||
this.layout( slide );
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Applies JS-dependent layout helpers for the given slide,
|
||||
* if there are any.
|
||||
*/
|
||||
layout( slide ) {
|
||||
|
||||
// Autosize text with the r-fit-text class based on the
|
||||
// size of its container. This needs to happen after the
|
||||
// slide is visible in order to measure the text.
|
||||
Array.from( slide.querySelectorAll( '.r-fit-text:not([data-fitted])' ) ).forEach( element => {
|
||||
element.dataset.fitted = '';
|
||||
Array.from( slide.querySelectorAll( '.r-fit-text' ) ).forEach( element => {
|
||||
fitty( element, {
|
||||
minSize: 24,
|
||||
maxSize: this.Reveal.getConfig().height * 0.8,
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
import { isAndroid } from '../utils/device.js'
|
||||
import { matches } from '../utils/util.js'
|
||||
|
||||
const SWIPE_THRESHOLD = 40;
|
||||
|
||||
|
@ -82,6 +83,9 @@ export default class Touch {
|
|||
*/
|
||||
isSwipePrevented( target ) {
|
||||
|
||||
// Prevent accidental swipes when scrubbing timelines
|
||||
if( matches( target, 'video, audio' ) ) return true;
|
||||
|
||||
while( target && typeof target.hasAttribute === 'function' ) {
|
||||
if( target.hasAttribute( 'data-prevent-swipe' ) ) return true;
|
||||
target = target.parentNode;
|
||||
|
|
10
js/reveal.js
10
js/reveal.js
|
@ -1335,7 +1335,11 @@ export default function( revealElement, options ) {
|
|||
}
|
||||
|
||||
// Announce the current slide contents to screen readers
|
||||
// Use animation frame to prevent getComputedStyle in getStatusText
|
||||
// from triggering layout mid-frame
|
||||
requestAnimationFrame( () => {
|
||||
announceStatus( getStatusText( currentSlide ) );
|
||||
});
|
||||
|
||||
progress.update();
|
||||
controls.update();
|
||||
|
@ -2290,7 +2294,7 @@ export default function( revealElement, options ) {
|
|||
// When looping is enabled `routes.down` is always available
|
||||
// so we need a separate check for when we've reached the
|
||||
// end of a stack and should move horizontally
|
||||
if( routes.down && routes.right && config.loop && isLastVerticalSlide( currentSlide ) ) {
|
||||
if( routes.down && routes.right && config.loop && isLastVerticalSlide() ) {
|
||||
routes.down = false;
|
||||
}
|
||||
|
||||
|
@ -2500,6 +2504,10 @@ export default function( revealElement, options ) {
|
|||
loadSlide: slideContent.load.bind( slideContent ),
|
||||
unloadSlide: slideContent.unload.bind( slideContent ),
|
||||
|
||||
// Preview management
|
||||
showPreview,
|
||||
hidePreview: closeOverlay,
|
||||
|
||||
// Adds or removes all internal event listeners
|
||||
addEventListeners,
|
||||
removeEventListeners,
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -47,12 +47,13 @@
|
|||
"gulp-connect": "^5.7.0",
|
||||
"gulp-eslint": "^6.0.0",
|
||||
"gulp-header": "^2.0.9",
|
||||
"gulp-sass": "^4.0.2",
|
||||
"gulp-sass": "^4.1.0",
|
||||
"gulp-tap": "^2.0.0",
|
||||
"gulp-zip": "^5.0.1",
|
||||
"highlight.js": "^10.0.3",
|
||||
"marked": "^1.1.0",
|
||||
"marked": "^2.0.3",
|
||||
"node-qunit-puppeteer": "^2.0.1",
|
||||
"node-sass": "^5.0.0",
|
||||
"qunit": "^2.10.0",
|
||||
"rollup": "^2.26.4",
|
||||
"rollup-plugin-terser": "^7.0.0",
|
||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -6,7 +6,7 @@
|
|||
|
||||
import marked from 'marked'
|
||||
|
||||
const DEFAULT_SLIDE_SEPARATOR = '^\r?\n---\r?\n$',
|
||||
const DEFAULT_SLIDE_SEPARATOR = '\r?\n---\r?\n',
|
||||
DEFAULT_NOTES_SEPARATOR = 'notes?:',
|
||||
DEFAULT_ELEMENT_ATTRIBUTES_SEPARATOR = '\\\.element\\\s*?(.+?)$',
|
||||
DEFAULT_SLIDE_ATTRIBUTES_SEPARATOR = '\\\.slide:\\\s*?(\\\S.+?)$';
|
||||
|
@ -234,7 +234,7 @@ const Plugin = () => {
|
|||
) );
|
||||
|
||||
}
|
||||
else if( section.getAttribute( 'data-separator' ) || section.getAttribute( 'data-separator-vertical' ) || section.getAttribute( 'data-separator-notes' ) ) {
|
||||
else {
|
||||
|
||||
section.outerHTML = slidify( getMarkdownFromSlide( section ), {
|
||||
separator: section.getAttribute( 'data-separator' ),
|
||||
|
@ -244,9 +244,6 @@ const Plugin = () => {
|
|||
});
|
||||
|
||||
}
|
||||
else {
|
||||
section.innerHTML = createMarkdownSlide( getMarkdownFromSlide( section ) );
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Loading…
Reference in New Issue