如何为AJAX加载的模态框视频绑定timeupdate进度条事件
timeupdate Event Binding for Dynamically Loaded Videos Got it, let's tackle this head-on. The core issue here is that your video element doesn't exist in the DOM when you initially try to bind the timeupdate event—since it's loaded later via $.get. Regular event binding won't work because it only targets elements present when the code runs. Here are two reliable solutions to get your custom progress bar working:
1. Bind the Event Directly After Loading the Video
The simplest approach is to wait until the video has been inserted into the DOM (right in your $.get callback) before attaching the timeupdate event. This ensures the video element exists when you try to target it.
$.get('/path/to/your/video-content', function(response) { // Inject the loaded content into your modal const modal = $('#your-modal-id'); modal.html(response); // Now grab the video and progress bar elements (adjust selectors to match your HTML) const video = modal.find('video')[0]; const progressSpan = modal.find('.custom-seekbar > span'); // Handle time updates to update the progress bar video.addEventListener('timeupdate', function() { // Make sure duration is available (videos load metadata asynchronously) if (!isNaN(this.duration)) { const progressPercent = (this.currentTime / this.duration) * 100; progressSpan.css('width', `${progressPercent}%`); } }); // Optional: Listen for metadata load to initialize the progress bar state video.addEventListener('loadedmetadata', function() { // Reset progress bar when video metadata is ready progressSpan.css('width', '0%'); }); });
Key Notes for This Method:
- Double-check your selectors: Ensure
videoand.custom-seekbar > spancorrectly target the elements in the loaded modal content. - Always check
isNaN(this.duration): Video duration isn't available immediately—this prevents NaN values from breaking your progress calculation.
2. Use a MutationObserver for Reusable Modals
If your modal is reused multiple times or you want a more automated approach, use a MutationObserver to watch for changes in the modal's DOM. This will automatically bind the timeupdate event whenever a video element is added to the modal.
// Target your modal container const modalContainer = document.getElementById('your-modal-id'); // Set up the observer to watch for new elements being added const observer = new MutationObserver(function(mutations) { mutations.forEach(function(mutation) { // Check if any added nodes are video elements const addedVideos = Array.from(mutation.addedNodes).filter(node => node.tagName === 'VIDEO'); addedVideos.forEach(video => { // Find the corresponding progress bar in the same modal context const progressSpan = $(video).closest('.modal-content').find('.custom-seekbar > span'); // Bind the timeupdate event video.addEventListener('timeupdate', function() { if (!isNaN(this.duration)) { const progressPercent = (this.currentTime / this.duration) * 100; progressSpan.css('width', `${progressPercent}%`); } }); // Initialize on metadata load video.addEventListener('loadedmetadata', function() { progressSpan.css('width', '0%'); }); }); }); }); // Configure the observer to watch for child elements being added observer.observe(modalContainer, { childList: true, subtree: true });
Why This Works:
- The observer listens for any new elements inserted into the modal, so you don't have to manually rebind events every time you load content via
$.get. - It's great for dynamic UIs where content is loaded/unloaded frequently.
Common Pitfalls to Avoid
- Don't use event delegation for
timeupdate: Unlike click or hover events,timeupdatedoesn't bubble up the DOM, so delegating to a parent element won't work. - Check for video errors: If the video fails to load,
durationwill remain NaN—add anerrorevent listener to handle this case if needed. - Clean up event listeners: If you're reusing the modal, remove old event listeners before loading new content to prevent memory leaks.
内容的提问来源于stack exchange,提问作者Dirty Bird Design

