Sascha Schulz
2023-08-30 55040a3cb40cb07cce44f2eada7774a264f4cdb9
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
/**
 * Creates a visual progress bar for the presentation.
 */
export default class Progress {
 
    constructor( Reveal ) {
 
        this.Reveal = Reveal;
 
        this.onProgressClicked = this.onProgressClicked.bind( this );
 
    }
 
    render() {
 
        this.element = document.createElement( 'div' );
        this.element.className = 'progress';
        this.Reveal.getRevealElement().appendChild( this.element );
 
        this.bar = document.createElement( 'span' );
        this.element.appendChild( this.bar );
 
    }
 
    /**
     * Called when the reveal.js config is updated.
     */
    configure( config, oldConfig ) {
 
        this.element.style.display = config.progress ? 'block' : 'none';
 
    }
 
    bind() {
 
        if( this.Reveal.getConfig().progress && this.element ) {
            this.element.addEventListener( 'click', this.onProgressClicked, false );
        }
 
    }
 
    unbind() {
 
        if ( this.Reveal.getConfig().progress && this.element ) {
            this.element.removeEventListener( 'click', this.onProgressClicked, false );
        }
 
    }
 
    /**
     * Updates the progress bar to reflect the current slide.
     */
    update() {
 
        // Update progress if enabled
        if( this.Reveal.getConfig().progress && this.bar ) {
 
            let scale = this.Reveal.getProgress();
 
            // Don't fill the progress bar if there's only one slide
            if( this.Reveal.getTotalSlides() < 2 ) {
                scale = 0;
            }
 
            this.bar.style.transform = 'scaleX('+ scale +')';
 
        }
 
    }
 
    getMaxWidth() {
 
        return this.Reveal.getRevealElement().offsetWidth;
 
    }
 
    /**
     * Clicking on the progress bar results in a navigation to the
     * closest approximate horizontal slide using this equation:
     *
     * ( clickX / presentationWidth ) * numberOfSlides
     *
     * @param {object} event
     */
    onProgressClicked( event ) {
 
        this.Reveal.onUserInput( event );
 
        event.preventDefault();
 
        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;
        }
 
        let targetIndices = this.Reveal.getIndices(slides[slideIndex]);
        this.Reveal.slide( targetIndices.h, targetIndices.v );
 
    }
 
    destroy() {
 
        this.element.remove();
 
    }
 
}