I've got a modal that opens a Youtube video. The modal is set to open whenever you reset the session.
I'm trying to make it so that when you close the modal (either by hitting the "x" or by clicking anywhere outside the modal) the youtube video stops playing, but I'm at a loss.
Here's my code so far:
//resetting/refreshing the session:
jQuery(document).ready(function(){
if (sessionStorage.getItem("story") !== 'true') {
sessionStorage.setItem("story", "true");
$("#myModal").modal();
}
$('#reset-session').on('click',function(){
sessionStorage.setItem('story','');
});
});
//my attempt at stopping the video:
function toggleVideo(state) {
// if state == 'hide', hide. Else: show video
var div = document.getElementById("myModal");
var iframe = div.getElementsByTagName("iframe")[0].contentWindow;
div.style.display = state == 'hide' ? 'none' : '';
func = state == 'hide' ? 'pauseVideo' : 'playVideo';
iframe.postMessage('{"event":"command","func":"' + func + '","args":""}','*');
}
body {
background-color: #335C64;
margin:10px;
}
h4 {
color: #FFD5C2;
}
.desc {
color: #FFD5C2;
margin-bottom: 4px;
}
.btn-sm {
margin-bottom: 15px;
}
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" integrity="sha384-MCw98/SFnGE8fJT3GXwEOngsV7Zt27NXFoaoApmYm81iuXoPkFOJwJ8ERdknLPMO" crossorigin="anonymous" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.0.0-alpha.6/js/bootstrap.min.js"></script>
<h4>Bootstrap Modal with SessionStorage</h4>
<hr />
<p class="desc">
Click this button to <strong>Refresh</strong> the page.
</p>
<a href="" id="refresh-page" class="btn btn-info btn-sm">
Refresh Page
</a>
<p class="desc">
Click this button to <strong>Reset</strong> and <strong>Refresh</strong> the page.
</p>
<a href="" id="reset-session" class="btn btn-warning btn-sm">
Reset Session
</a>
<div class="modal fade" id="myModal" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal">×</button>
<h4 class="modal-title text-primary">Victor Frankenstein</h4>
</div>
<div class="modal-body">
<iframe width="560" height="315" src="https://www.youtube.com/embed/VZzZKuQUguk" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen></iframe></div>
<div class="modal-footer">
<button type="button" class="btn btn-default btn-sm" data-dismiss="modal"> Close </button>
</div>
</div>
</div>
</div>
Here's a codepen: https://codepen.io/jackcode1/pen/ZEpbRQq
I found an easy, perhaps too easy, solution:
$("#myModal").on('hidden.bs.modal', function (e) {
$("#myModal iframe").attr("src", $("#myModal iframe").attr("src"));
});
That's it. I guess I was over complicating this.
Related
Hello I have a 2 buttons trailer and movie, I want to play the video based on the button I clicked.
For example I choose Trailer then it should play trailer and vice versa
here is my button
<button class="btn btn-sm btn-dark" id="trailer" data-toggle="modal" data-target="#myModal2">Trailer</button>
<button class="btn btn-sm btn-dark" id="movieNoads" data-toggle="modal" data-target="#myModal2">Movie</button>
here is my video player and its javascript codes
<video controls playsinline id="player" width="100%">
<script type="text/javascript">
var video = document.getElementById('video');
var source = document.createElement('source');
document.getElementById('trailer').onclick = function () {
source.setAttribute('src', '../inflightapp/storage/app/public/trailer_videos/<?php echo ''.$row2['trailer_video'].''; ?>');
video.appendChild(source);
video.play();
}
document.getElementById('movieNoads').onclick = function () {
source.setAttribute('src', '../inflightapp/storage/app/public/movie_videos/<?php echo ''.$row2['movie_video'].''; ?>');
video.appendChild(source);
video.play();
}
</script>
</video>
You forgot to load the video
"use strict";
console.clear();
const video = document.getElementById("player");
const source = document.createElement("source");
function loadVideo(element, src) {
source.src = src;
element.appendChild(source);
element.load();
element.play();
}
document.getElementById("trailer").addEventListener(
'click',
() => loadVideo(
video,
"https://s3-us-west-2.amazonaws.com/s.cdpn.io/96344/lego.mp4"
)
)
document.getElementById("movieNoads").addEventListener(
'click',
() => loadVideo(
video,
"https://s3-us-west-2.amazonaws.com/s.cdpn.io/96344/abstract-001.mp4"
)
)
<button class="btn btn-sm btn-dark" id="trailer" data-toggle="modal" data-target="#myModal2">Trailer</button>
<button class="btn btn-sm btn-dark" id="movieNoads" data-toggle="modal" data-target="#myModal2">Movie</button>
<video controls playsinline id="player" width="100%" loop></video>
You can have a look at this.
<button class="btn btn-sm btn-dark" id="trailer">Trailer</button>
<button class="btn btn-sm btn-dark" id="movieNoads">Movie</button>
<script type="text/javascript">
var trailer = document.getElementById('trailer');
trailer.setAttribute('data-toggle', 'modal');
trailer.setAttribute('data-target', '#myModal2');
var movieNoads = document.getElementById('movieNoads');
movieNoads.setAttribute('data-toggle', 'modal');
movieNoads.setAttribute('data-target', '#myModal2');
</script>
<video controls playsinline id="player" width="100%">
<script type="text/javascript">
var video = document.getElementById('player');
document.getElementById('trailer').onclick = function () {
document.getElementById("player").style.display = "block";
video.setAttribute('src', 'YouVideoURLHere');
video.play();
}
document.getElementById('movieNoads').onclick = function () { document.getElementById("player").style.display = "block";
video.setAttribute('src', 'YourVideoURLHere');
video.play();
}
document.getElementById("player").style.display = "none";
</script>
</video>
You Can try this
function setvideo(src) {
document.getElementById('div_video').innerHTML = '<video autoplay controls id="video_ctrl" style=" width: 100%;"><source src="'+src+'" type="video/mp4"></video>';
document.getElementById('video_ctrl').play();
}
<!DOCTYPE html>
<html>
<body>
<div id="div_video"> </div>
<button onClick="setvideo('movie.mp4')"> Trailer</button>
<button onClick="setvideo('mov_bbb.mp4')"> Movie</button>
</body>
</html>
Welcome to Stack Overflow. You could try something along the lines of the following:
I used jQuery and Bootstrap (as I noticed you used Bootstrap HTML elements).
//Custom function to populate a modal. This could be expanded on to even add a destination parameter in order to use seperate modals (e.g. function videoModal(destination, source) and replace #myModal2 with the `destination` parameter).
function videoModal(source) {
$("#myModal2 .modal-body").html($("video#player").clone());
//Add your second source:
$("#myModal2 video#player > source").attr("src", source);
$("#myModal2 .modal-body video#player").css("display", "block");
}
$(document).ready(function() {
//On init, save current loaded state of modal
let modalInit = $("#myModal2 .modal-body").html();
//On interaction with a control
$("body").on("click", "button#trailer", function() {
//Populate modal
videoModal("https://www.w3schools.com/tags/movie.mp4");
});
$("body").on("click", "button#movieNoads", function() {
//Populate modal
videoModal("https://www.w3schools.com/html/mov_bbb.mp4")
});
//Reset modal on close
$("#myModal2").on('hidden.bs.modal', function(e) {
$("#myModal2 .modal-body").html(modalInit);
});
});
video#player {
display: none;
margin-left: auto;
margin-right: auto;
}
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js"></script>
<!-- Modal -->
<div class="modal fade" id="myModal2" tabindex="-1" role="dialog" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalLabel">Modal title</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
<div class="modal-body">
...
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-dismiss="modal">Close</button>
<button type="button" class="btn btn-primary">Save changes</button>
</div>
</div>
</div>
</div>
<video id="player" controls autoplay loop>
<source src="" type="video/mp4">
</video>
<!-- Button trigger modal -->
<button type="button" id="trailer" class="btn btn-primary" data-toggle="modal" data-target="#myModal2">
Trailer
</button>
<button type="button" id="movieNoads" class="btn btn-primary" data-toggle="modal" data-target="#myModal2">
Movie
</button>
JSFiddle
This way you could also load the videos inside modals (as I noticed you were trying to use modal buttons). No refreshes are required.
After closing modal window the i frame element keeps playing and I don't have a clue how to refer to proper element in JS.
The trick is that I use PHP variable as an ID to generate and use multiple modal windows straight from my database.
The code goes as follows:
foreach ($movieId as $data) {
echo '<div class="card card-movie-poster bg-blacker text-white text-center text-align-middle mx-2 mb-3">
<div class="card-body">
<a data-toggle="modal" href="#myModal'.$data['movieID'].'"><img class="card-img " src="img/movieCovers/'.$data['datatitle'].'.jpg"></a>
</div>
</div>';}
And
foreach ($movieId as $datatitle) {
echo '<div class="modal fade" id="myModal'.$data['movieID'].'">
<div class="modal-dialog modal-lg modal-dialog-centered" role="document">
<div class="modal-content bg-black">
<div class="modal-header">
<!-- Movie Title -->
<h3 class="text-white-50">'.$data['movieTitle'].'</h3>
<!-- Close button -->
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
<div class="modal-body container">
<!-- Video -->
<div class="embed-responsive embed-responsive-16by9">
<iframe id="'.$data['movieID'].'" class="embed-responsive-item" src="https://www.youtube-nocookie.com/embed/'.$data['videoUrl'].'?rel=0&showinfo=0" frameborder="0" allow="autoplay; encrypted-media" allowfullscreen></iframe>
</div>
</div>
</div>
</div>
';}
You can try:
$("#myModal").on('hidden.bs.modal', function (e) {
$("#myModal iframe").attr("src", $("#myModal iframe").attr("src"));
});
OK then.
Finally did it myself:
var grabbed = document.querySelectorAll('[id^="myModal"]');
var myModal;
var innerIframe;
for (var i = 0; i < grabbed.length; i++) {
// console.log(grabbed[i].id);
$(grabbed[i]).on('show.bs.modal', function () {
myModal = this.id;
// console.log(this.id);
})
$(grabbed[i]).on('hide.bs.modal', function () {
// console.log(this.id + " closed");
innerIframe = this.getElementsByClassName('embed-responsive-item');
$('iframe').attr('src', $('iframe').attr('src'));
// console.log(innerIframe[0]);
});
}
On the page I have a button with several data attributes, title and audioURL. One click, I have some javascript that populates a modal window with the title, and simple html5 audio player with the data-audioURL in the src attribute. Once that is complete, I initialize MediaElement. On success, I play the audio.
When the user closes the modal window, I want to remove the MediaElement so that another button with a different title and audioURL can populate the audio player and then reinitialize MediaElement. Currently, the code I have succeeds to stop the audio playback, but it doesn't destroy the player.
HTML:
<button type="button" class="btn btn-info btn-lg btn-block" data-toggle="modal" data-target="#closerLook" data-title="Song Title" data-audio="audio.mp3"><i class="fa fa-headphones" aria-hidden="true"></i> Hear a Sample</button>
<div class="modal fade" id="closerLook" tabindex="-1" role="dialog">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
<h4 class="modal-title text-center">Audio Modal</h4>
</div>
<div class="modal-body">
<h3 id="cl-title" class="text-center"></h3>
<audio id="audioSample" preload="meta" tabindex="0" controls><source src=""/></audio>
</div>
</div>
</div>
JS:
$(document).ready(function(){
var me;
$('#closerLook').on('shown.bs.modal', function (event) {
$('#audioSample').attr("src", "");
var button = $(event.relatedTarget);
var theTitle = button.data('title');
var theAudio = button.data('audio');
var modal = $(this);
modal.find('#cl-title').text(theTitle);
$('#audioSample').attr("src", theAudio);
loadPlayer();
});
$('#closerLook').on('hide.bs.modal', function (event) {
console.log(me);
me.remove();
});
});
function loadPlayer() {
$('#audioSample').mediaelementplayer({
audioWidth: '100%',
success: function(mediaElement, originalNode, instance) {
mediaElement.play();
me = mediaElement;
}
});
}
I know I'm missing something in the hide.bs.modal function to properly remove the player, I just don't know what. Thanks in advance.
move var me out of document.ready and initialize the variable inside the success function with instance see the working example below
var me;
$(document).ready(function() {
$('#closerLook').on('shown.bs.modal', function(event) {
let button = $(event.relatedTarget);
let theTitle = button.data('title');
let theAudio = button.data('audio');
let modal = $(this);
modal.find('#cl-title').text(theTitle);
//setSrc (src)
$('#audioSample').attr("src", theAudio);
loadPlayer();
});
$('#closerLook').on('hide.bs.modal', function(event) {
console.log('removing');
//me.pause();
me.remove()
});
});
function loadPlayer() {
$('#audioSample').mediaelementplayer({
audioWidth: '100%',
error:function(mediaElement, originalNode, instance) {
console.log('error');
},
success: function(mediaElement, originalNode, instance) {
console.log('success');
console.log(mediaElement)
instance.play();
me = instance;
}
});
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet" />
<link href="https://cdnjs.cloudflare.com/ajax/libs/mediaelement/4.2.7/mediaelementplayer.min.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/mediaelement/4.2.7/mediaelement-and-player.min.js"></script>
<button type="button" class="btn btn-info btn-lg btn-block" data-toggle="modal" data-target="#closerLook" data-title="SoundHelix" data-audio="https://www.soundhelix.com/examples/mp3/SoundHelix-Song-1.mp3"><i class="fa fa-headphones" aria-hidden="true"></i> Hear a Sample</button>
<div class="modal fade" id="closerLook" tabindex="-1" role="dialog">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
<h4 class="modal-title text-center">Audio Modal</h4>
</div>
<div class="modal-body">
<h3 id="cl-title" class="text-center"></h3>
<audio id="audioSample" preload="meta" tabindex="0" controls><source src=""/></audio>
</div>
</div>
</div>
Here is some code where when you click on a link/image, an embedded youtube video is revealed as an overlay, similar to a lightbox effect.
When I have one video set up, the video will stop playing when I click on the 'x' to closer the popup/overlay.
If I add more videos, the video continues to play in the background. The overlay is hidden but the audio still runs.
Can you help me find out how to stop the video? I need a total of 6 videos on a page.
HTML:
<div class="col-xs-12 col-sm-6 col-md-6 col-lg-4">
<a onclick="startoverlay()" href="#" title="Watch video" class="flex-item box-link bg-lightgrey fg-darkgrey">
<div class="tiled-image" id="img0">
<div class="tiled-overlay">
<h3 class="sm-title hblack text-uppercase"><strong class="fg-white"> <span class="fa fa-play" aria-label="Play"></span> </strong></h3> </div>
</div>
<div class="tiled-body">
<p>text</p>
</div>
</a>
</div>
<div class="col-xs-12 col-sm-6 col-md-6 col-lg-4">
<a onclick="startoverlay2()" href="#" title="Watch video" class="flex-item box-link bg-lightgrey fg-darkgrey">
<div class="tiled-image" id="img0">
<div class="tiled-overlay">
<h3 class="sm-title hblack text-uppercase"><strong class="fg-white"> <span class="fa fa-play" aria-label="Play"></span> </strong></h3> </div>
</div>
<div class="tiled-body">
<p>text</p>
</div>
</a>
</div>
Overlays:
<!-- VIDEO ONE OVERLAY-->
<div id="overlay" class="modal" role="dialog" aria-labelledby="modal-video-label">
<div class="modal-dialog modal-full" role="document">
<div class="modal-content">
<div class="modal-header text-right">
<button type="button" class="close" id="close-button" onclick="startoverlay()" aria-label="Close"> <span aria-hidden="true">×</span> </button>
</div>
<div class="modal-body">
<div class="modal-video">
<div class="embed-responsive embed-responsive-16by9">
<iframe id="video" class="embed-responsive-item" src="https://www.youtube.com/embed/6HOlHZfqzxk?enablejsapi=1" frameborder="0"></iframe>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- VIDEO TWO OVERLAY-->
<div id="overlay2" class="modal" role="dialog" aria-labelledby="modal-video-label">
<div class="modal-dialog modal-full" role="document">
<div class="modal-content">
<div class="modal-header text-right">
<button type="button" class="close" id="close-button" onclick="startoverlay2()" aria-label="Close"> <span aria-hidden="true">×</span> </button>
</div>
<div class="modal-body">
<div class="modal-video">
<div class="embed-responsive embed-responsive-16by9">
<iframe id="video" class="embed-responsive-item" src="https://www.youtube.com/embed/o1aVMcrb4aE?enablejsapi=1" frameborder="0"></iframe>
</div>
</div>
</div>
</div>
</div>
</div>
<div id="modal-backdrop" class="modal-backdrop fade in"></div>
JavaScript:
For the second part of the script I have duplicated the overlay code and called it startoverlay2 - I am not sure if that is correct.
<script type="text/javascript">a
var player;
function onYouTubePlayerAPIReady() {
player = new YT.Player('video', {
events: {
'onReady': onPlayerReady
}
});
}
function onPlayerReady(event) {
var pauseButton = document.getElementById('close-button');
pauseButton.addEventListener('click', function() {
player.pauseVideo();
});
}
var tag = document.createElement('script');
tag.src = '//www.youtube.com/player_api';
var firstScriptTag = document.getElementsByTagName('script')[0];
firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
</script>
<!-- /* overlays */ -->
<!-- /* OVERLAY 1 */ -->
<script type="text/javascript">
function startoverlay() {
el = document.getElementById("overlay");
el.style.display = (el.style.display == "block") ? "none" : "block";
els = document.getElementById("modal-backdrop");
els.style.display = (els.style.display == "block") ? "none" : "block";
}
</script>
<!-- /* OVERLAY 2 */ -->
<script type="text/javascript">
function startoverlay2() {
el = document.getElementById("overlay2");
el.style.display = (el.style.display == "block") ? "none" : "block";
els = document.getElementById("modal-backdrop");
els.style.display = (els.style.display == "block") ? "none" : "block";
}
</script>
I do wonder if I need to do something to the pauseButton var?
To resolve this, it looks like you need to tell the video to stop playing. As you're using the iframe version of the YouTube player, we can do this by replacing it's src tag with the same value.
// get the video's surrounding overlay
el = document.getElementById("overlay");
// hide the overlay, or show it if it's already hidden
el.style.display = (el.style.display == "block") ? "none" : "block";
// Restart the video (paused)
var videoIFrame = el.querySelector('iframe');
srcUrl = videoIFrame.getAttribute('src');
videoIFrame.setAttribute('src', srcUrl);
This causes the video to be reloaded, taking you back to the (paused) start state, ready for the modal to be opened again.
If you want to pause the video in its current place, you'll want to consider using the API rather than the iframe option.
It's a bit outside the scope of the question, but there's also some refactoring you could do to reduce the code repetition, for example pulling the JS into a single 'hide' function:
function stopAndHide(element) {
element.style.display = "none";
// Restart the video (paused)
var videoIFrame = element.querySelector('iframe');
srcUrl = videoIFrame.getAttribute('src');
videoIFrame.setAttribute('src', srcUrl);
els = document.getElementById("modal-backdrop");
els.style.display = "none";
}
and then calling it from the HTML as follows:
<button type="button" class="close" onclick="stopAndHide(this)" aria-label="Close"> <span aria-hidden="true">×</span> </button>
I have an issue where I'm attempting to use a URL to open a Modal in window B, by clicking on an image link in window A. The image itself is setup inside an anchor tag, such that <a href="myserver.mydestinationB.com#myModal><img src='myImage'></a> is in window A.
How can I get to window B AND open the modal only using the URL, if possible.
Code :
Page A
<a href="http://www.x.com/#DesiredModalID">
<img typeof="foaf:Image" src="http://google.com/image.png" width="1920" height="1080" alt="">
</a>
Page B
<div class="modal fade" id="myModal" role="dialog">
<div class="modal-dialog"><!-- Modal content-->
<div class="modal-content">
<div class="modal-header"><button id="modalclose" class="close" data- dismiss="modal" type="button">×</button>
<h4 class="modal-title" id="header-data">Modal Header</h4>
</div>
<div class="modal-body">
<p id="modal-text">Some text in the modal.</p>
<div id="modal-body" style="text-align: center;"> </div>
</div>
<div class="modal-footer">
<h5 id="footer-data" style="font-weight:bold;font-style:italic;float:left;">Test Data</h5>
<button class="btn btn-default" data-dismiss="modal" id="closetwo" type="button">Close</button></div>
</div>
</div>
<img id="myimage" src='myImage'>
<script>
$(document).ready(function(){
$("#myimage").click(function() {
$("#myModal").modal();
})
})
</script>
<a href="myserver.mydestinationB.com?mymodal=open>
--- On Page B you add script ---
<script>
$(document).ready(function(){
var mymodal = $_GET('mymodal');
if(mymodal != null){
$("#myModal").modal();
}
})
function $_GET(param) {
var vars = {};
window.location.href.replace( location.hash, '' ).replace(
/[?&]+([^=&]+)=?([^&]*)?/gi, // regexp
function( m, key, value ) { // callback
vars[key] = value !== undefined ? value : '';
}
);
if ( param ) {
return vars[param] ? vars[param] : null;
}
return vars;
}
</script>