<main id="page-wrapper">
    
    <!-- Eléménts cliquables -->
    <p>
        <a class="link-media" data-mediatype="img" href="https://res.cloudinary.com/dnqehhgmu/image/upload/v1509718497/sea_ej0zoc.jpg" title="Envie d'évasion ?">Ouverture d'une image</a>
    </p>
    <p>
        <a class="link-media" data-mediatype="video" href="https://res.cloudinary.com/dnqehhgmu/video/upload/v1509981466/rickroll_w11xqz.mp4" title="Never gonna give you up">Ouverture d'une vidéo</a>
    </p>
    <p>
        <a class="link-media" data-mediatype="pdf" href="http://res.cloudinary.com/dnqehhgmu/image/upload/v1509980892/24joursdeweb_pcxw8n.pdf" title="Les frameworks, c'est pas automatique !">Ouverture d'un pdf</a>
    </p>
    <p>
        <a class="link-media" data-mediatype="iframe" href="https://www.24joursdeweb.fr/2017/lancement/" title="24 jours de Web 2017">Ouverture d'une iframe</a>
    </p>
    
</main>

<!-- Fenêtre modale -->
<aside id="fullPage-alert" class="fullPage-alert hidden" aria-hidden="true">
    <div id="fullPage-alert-container" class="fullPage-alert-container" role="dialog">
        <button type="button" id="fullPage-alert-close" class="fullPage-alert-close" aria-label="Fermer"></button>
        <div id="fullPage-alert-content" class="fullPage-alert-content"></div>
        <div class="fullPage-alert-title-wrapper">
            <h4 id="fullPage-alert-title" class="fullPage-alert-title"></h4>
        </div>
    </div>
</aside>
body {
  margin: 0;
  font-family: "Open Sans", Arial, sans-serif;
  font-size: 14px;
}

body .hidden {
  display: none;
}

/* Alter container */

.fullPage-alert {
  z-index: 10;
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  padding: 20px;
  display: -webkit-box;
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-align: center;
  -webkit-align-items: center;
  -ms-flex-align: center;
  align-items: center;
  -webkit-box-pack: center;
  -webkit-justify-content: center;
  -ms-flex-pack: center;
  justify-content: center;
  background-color: rgba(0,0,0,0.85);
  -webkit-transition: opacity 0.35s ease-out;
  transition: opacity 0.35s ease-out;
}

.fullPage-alert-container {
  position: relative;
}

.fullPage-alert-container.fullPage {
  width: 100%;
  height: 100%;
}

/* Alert title and close */

.fullPage-alert-title-wrapper {
  position: absolute;
  bottom: -15px;
  left: 15px;
  right: 15px;
  display: -webkit-box;
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-pack: center;
  -webkit-justify-content: center;
  -ms-flex-pack: center;
  justify-content: center;
}

.fullPage-alert-title {
  margin: 0;
  padding: 0 10px;
  line-height: 24px;
  border-radius: 10px;
  border: 3px solid #FFF;
  background-color: #0463B3;
  color: #FFF;
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}

.fullPage-alert-close {
  z-index: 2;
  position: absolute;
  top: -16px;
  right: -16px;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  background-color: #0463B3;
  background-image: url("https://res.cloudinary.com/dnqehhgmu/image/upload/v1509980709/white-cross_kaqkmp.svg");
  background-size: 14px 14px;
  background-position: center;
  background-repeat: no-repeat;
  border: 3px solid #FFF;
  cursor: pointer;
  -webkit-transition: background-size 0.15s ease-out;
  transition: background-size 0.15s ease-out;
}

.fullPage-alert-close:hover,
.fullPage-alert-close:focus {
  background-size: 20px 20px;
}

/* Alert content */

.fullPage-alert-content {
  box-sizing: border-box;
  z-index: 1;
  height: 100%;
 display: -webkit-box;
  display: -webkit-flex;
  display: -ms-flexbox;
  display: flex;
  padding: 0;
  overflow: auto;
  border: 3px solid #FFF;
  border-radius: 5px;
  background-color: #000;
}

.fullPage-iframe,
.fullPage-object {
  display: block;
  width: 100%;
  height: 100%;
  -webkit-overflow-scrolling: touch;
  border: none;
  overflow: auto;
}

.fullPage-image,
.fullPage-video {
  max-width: calc(100vw - 46px);
  max-height: calc(100vh - 46px);
}

/* Link display */

.link-media {
  display: block;
  width: 180px;
  padding: 10px;
  margin-left: 20px;
  text-align: center;
  border-radius: 5px;
  background-color: #0463B3;
  color: #FFF;
  text-decoration: none;
  -webkit-transition: background-color 0.25s ease-out;
  transition: background-color 0.25s ease-out;
}

.link-media:hover,
.link-media:focus {
  background-color: #3AA996;
}
/*
 * Elément cliquable ayant déclenché l'ouverture modale en cours
 */
var alertOpener;

/*
 * Eléments navigables du corps de page
 */
var navTabs = [];

/*
 * Tabindex des éléments navigables du corps de page
 */
var navTabsTabindex = [];

/*
 * Traitement de tous les media en affichage modal
 */
var mediaLinks = document.getElementsByClassName('link-media');
var mediaLinksNb = mediaLinks.length;
for (var i=0;i<mediaLinksNb;i++) {
	mediaLinks[i].addEventListener('click', function(e) {
		
        e.preventDefault();
        
        // Récupération des valeurs
        if (!this.href) {
            return;
        }
        var href = this.href;
        var title = '';
        if (this.title) {
            title = this.title;
        }
        var mediaText = '';
        var isFullPage = false;
        
        // Switch selon le type de media
        switch (this.getAttribute('data-mediatype')) {
            
            // Ouverture modale d'une image
            case 'img' :
                mediaText = '<img src="'+href+'" alt="'+title+'" class="fullPage-image" />';
                break;
            
            // Ouverture modale d'une video
            case 'video' :
                mediaText = '<video class="fullPage-video" itemprop="url" title="'+title+'" alt="'+title+'" controls autoplay>';
                mediaText += '<source itemprop="url" content="'+window.location.protocol+'//'+window.location.hostname+href+'" src="'+href+'" type="video/mp4" />';
                mediaText += '<a href="'+href+'" download>'+title+'</a>';
                mediaText += '</video>';
                break;
            
            // Ouverture modale d'un pdf
            case 'pdf' :
                mediaText = '<object class="fullPage-object" data="'+href+'" type="application/pdf"></object>';
                isFullPage = true;
                break;
            
            // Ouverture modale d'une iframe
            case 'iframe' :
                mediaText = '<iframe class="fullPage-iframe" src="'+href+'" allowfullscreen></iframe>';
                isFullPage = true;
                break;
            
        }
		
        // Affichage de la fenetre
        if (mediaText!='') {
            displayFullPageAlert(mediaText,title,isFullPage);
            alertOpener = this;
        }
        
	},false);
}


/**
 * Affichage de la fenetre modale et remplissage de son contenu
 */
function displayFullPageAlert(content,title,isFullPage,openerId) {
	
    // Remplissage du contenu
    document.getElementById('fullPage-alert-content').innerHTML = content;
    if (title!='') {
        document.getElementById('fullPage-alert-title').textContent = title;
        document.getElementById('fullPage-alert-title').className = 'fullPage-alert-title';
    }
    if (isFullPage) {
        document.getElementById('fullPage-alert-container').className = 'fullPage-alert-container fullPage';
    } else {
        document.getElementById('fullPage-alert-container').className = 'fullPage-alert-container';
    }
	
    // Apparition fondue
    document.getElementById('fullPage-alert').style.opacity = '0';
	document.getElementById('fullPage-alert').className = 'fullPage-alert';
    
    // Accessibilité (aria + navigation clavier)
    document.getElementById('fullPage-alert').removeAttribute('aria-hidden');
    document.getElementById('page-wrapper').setAttribute('aria-hidden','true');
    disableMainNavTab();
	
    // Apparition totale
    setTimeout(function() {
		document.getElementById('fullPage-alert').style.opacity = '1';
		document.documentElement.style.overflow = 'hidden';
        // Focus sur la croix de fermeture
        document.getElementById('fullPage-alert-close').focus();
	},350);
    
}

/*
 * Fermeture de la fenêtre modale par clic ou echap
 */
document.getElementById('fullPage-alert-close').addEventListener('click',closeFullPageAlert,false);
document.addEventListener('keydown',function(e) {
	var code = e.keyCode || e.which;
	if (code === 27 && document.getElementById('fullPage-alert').className.indexOf('hidden')==-1) {
		closeFullPageAlert();
	} 
},false);

/**
 * Fermeture de la fenêtre modale
 */
function closeFullPageAlert() {
    
    // Disparition fondue
    document.documentElement.style.overflow = '';
    document.getElementById('fullPage-alert').style.opacity = '0';
    
    // Accessibilité (aria + navigation clavier)
    document.getElementById('fullPage-alert').setAttribute('aria-hidden','true');
    document.getElementById('page-wrapper').removeAttribute('aria-hidden');
    repairMainNavTab();
    
    // Focus de retour sur l'élément ayant déclenché l'ouverture modale
    alertOpener.focus();
    
    // Disparition totale
    setTimeout(function() {
        document.getElementById('fullPage-alert').className = 'fullPage-alert hidden';
        document.getElementById('fullPage-alert-content').innerHTML = '';
        document.getElementById('fullPage-alert-title').textContent = '';
        document.getElementById('fullPage-alert-title').className = 'fullPage-alert-title hidden';
    },350);
    
}

/**
 * Fonction désactivant la navigation clavier derrière la modale
 */
function disableMainNavTab() {
    navTabs = document.getElementById('page-wrapper').querySelectorAll('a[href], area[href], input:not([disabled]), select:not([disabled]), textarea:not([disabled]), button:not([disabled]), [tabindex]:not([tabindex^="-"]), iframe, object');
    var navTabsNb = navTabs.length;
    navTabsTabindex = [];
    for (var i=0;i<navTabsNb;i++) {
        // Garde en mémoire les valeurs de tabindex
        var tabIndex = navTabs[i].getAttribute('tabindex');
        if (tabIndex==null) {
            navTabsTabindex[i] = tabIndex
        } else {
            navTabsTabindex[i] = -9999;
        }
        // Bloque la navigation clavier
        navTabs[i].setAttribute('tabindex','-1');
    }
}

/**
 * Fonction réactivant la navigation clavier derrière la modale
 */
function repairMainNavTab() {
    var navTabsNb = navTabs.length;
    for (var i=0;i<navTabsNb;i++) {
        // Réinitialise les valeurs de tabindex
        var tabIndex = navTabsTabindex[i];
        if (navTabsTabindex[i] = -9999) {
            navTabs[i].removeAttribute('tabindex');
        } else {
            navTabs[i].setAttribute('tabindex',tabIndex);
        }
    }
}

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

This Pen doesn't use any external JavaScript resources.