Video Player
HesedVid Video Player
Embed HesedVid’s custom video player directly into your applications using our iframe-based player. The player provides a professional, customizable video experience with built-in controls, analytics, and responsive design.
Overview
The HesedVid player is a fully-featured HTML5 video player designed for seamless integration:
- Iframe Embedding: Easy integration with any web application
- Customizable UI: Branded player experience with your colors and logo
- Analytics Integration: Built-in viewer engagement tracking
- Responsive Design: Automatically adapts to different screen sizes
- Multiple Formats: Supports HLS, MP4, and other video formats
- Accessibility: WCAG compliant with keyboard navigation and screen reader support
Player URL Structure
The HesedVid player supports public and private URL formats:
https://player.hesedvid.com/v1/private/{publicID}/master.m3u8https://player.hesedvid.com/v1/public/{org_id}/{env_id}/{vid_id}/master.m3u8URL Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
autoplay | boolean | No | false | Auto-start video playback (true in iframes) |
muted | boolean | No | false | Start video muted (true in iframes) |
controls | boolean | No | true | Show native player controls |
poster | string | No | - | URL to poster image |
quality | string | No | auto | Initial quality selection. One of: auto, highest, lowest, or a height like 2160p, 1440p, 1080p, 720p, 480p, 360p, 240p, 144p. Numbers without p are accepted. ABR remains enabled after startup. |
high | boolean | No | false | Deprecated alias for quality=highest (backward compatible) |
signed | string | No | - | Signed URL for private videos (contains token) |
token | string | No | - | Token for private videos (alternative to signed) |
Performance Presets
For viewers with known good bandwidth, start at top quality:
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?autoplay=true&muted=true&quality=highest"></iframe>Force a specific starting quality
<!-- Start at 1080p, then ABR adapts --><iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?autoplay=true&muted=true&quality=1080p"></iframe>Start at the lowest quality
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?autoplay=true&muted=true&quality=lowest"></iframe>Private Video with Token
For videos requiring authentication:
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?token=abc123&autoplay=true&muted=true"></iframe>Note: Advanced Shaka tuning (buffer goals, ABR targets, etc.) isn’t exposed via URL. The player uses optimized defaults to minimize startup requests and keep playback stable.
Basic Embedding
HTML Iframe
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8" width="800" height="450" frameborder="0" allowfullscreen></iframe>Responsive Embedding
<div class="video-container" style="position: relative; width: 100%; height: 0; padding-bottom: 56.25%;"> <iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8" style="position: absolute; top: 0; left: 0; width: 100%; height: 100%;" frameborder="0" allowfullscreen> </iframe></div>Advanced Configuration
Custom Player Settings
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?autoplay=true&muted=true&theme=dark&branding=false" width="800" height="450" frameborder="0" allowfullscreen></iframe>Dynamic URL Generation
// Generate player URL with custom settingsfunction createPlayerUrl(videoId, options = {}) { const baseUrl = 'https://player.hesedvid.com'; const params = new URLSearchParams();
if (options.autoplay) params.append('autoplay', 'true'); if (options.muted) params.append('muted', 'true'); if (options.theme) params.append('theme', options.theme); if (options.branding === false) params.append('branding', 'false');
const queryString = params.toString(); return queryString ? `${baseUrl}/${videoId}?${queryString}` : `${baseUrl}/${videoId}`;}
// Usageconst playerUrl = createPlayerUrl('pubvid_AbCdEf', { autoplay: true, muted: true, theme: 'dark', branding: false});
// Update iframe srcdocument.getElementById('player').src = playerUrl;import React, { useState, useEffect } from 'react';
const HesedVidPlayer = ({ videoId, autoplay = false, muted = false, theme = 'auto', branding = true }) => { const [playerUrl, setPlayerUrl] = useState('');
useEffect(() => { const params = new URLSearchParams(); if (autoplay) params.append('autoplay', 'true'); if (muted) params.append('muted', 'true'); if (theme !== 'auto') params.append('theme', theme); if (!branding) params.append('branding', 'false');
const queryString = params.toString(); const url = queryString ? `https://player.hesedvid.com/${videoId}?${queryString}` : `https://player.hesedvid.com/${videoId}`;
setPlayerUrl(url); }, [videoId, autoplay, muted, theme, branding]);
return ( <div className="video-container" style={{ position: 'relative', width: '100%', height: 0, paddingBottom: '56.25%' }}> <iframe src={playerUrl} style={{ position: 'absolute', top: 0, left: 0, width: '100%', height: '100%' }} frameBorder="0" allowFullScreen title={`HesedVid Player - ${videoId}`} /> </div> );};
// Usage<HesedVidPlayer videoId="pubvid_AbCdEf" autoplay={false} muted={false} theme="dark" branding={false}/><template> <div class="video-container" :style="containerStyle"> <iframe :src="playerUrl" style="position: absolute; top: 0; left: 0; width: 100%; height: 100%;" frameborder="0" allowfullscreen :title="`HesedVid Player - ${videoId}`" /> </div></template>
<script setup>import { computed } from 'vue';
const props = defineProps({ videoId: { type: String, required: true }, autoplay: { type: Boolean, default: false }, muted: { type: Boolean, default: false }, theme: { type: String, default: 'auto' }, branding: { type: Boolean, default: true }});
const playerUrl = computed(() => { const params = new URLSearchParams(); if (props.autoplay) params.append('autoplay', 'true'); if (props.muted) params.append('muted', 'true'); if (props.theme !== 'auto') params.append('theme', props.theme); if (!props.branding) params.append('branding', 'false');
const queryString = params.toString(); return queryString ? `https://player.hesedvid.com/${props.videoId}?${queryString}` : `https://player.hesedvid.com/${props.videoId}`;});
const containerStyle = { position: 'relative', width: '100%', height: 0, paddingBottom: '56.25%'};</script>Player Themes
Light Theme
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?theme=light"></iframe>Dark Theme
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?theme=dark"></iframe>Auto Theme (Default)
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?theme=auto"></iframe>The auto theme automatically switches between light and dark based on the user’s system preference.
Player Events (PostMessage API)
The HesedVid player supports communication with the parent page through the PostMessage API:
Listening for Player Events
window.addEventListener('message', function(event) { // Verify origin for security if (event.origin !== 'https://player.hesedvid.com') { return; }
const data = event.data;
switch (data.type) { case 'playerReady': console.log('Player is ready'); break;
case 'play': console.log('Video started playing'); break;
case 'pause': console.log('Video paused'); break;
case 'ended': console.log('Video ended'); break;
case 'timeUpdate': console.log('Current time:', data.currentTime); break;
case 'volumeChange': console.log('Volume changed:', data.volume); break;
case 'error': console.error('Player error:', data.error); break; }});Controlling the Player
// Send commands to the playerfunction sendPlayerCommand(command, data = {}) { const iframe = document.getElementById('player'); iframe.contentWindow.postMessage({ type: command, ...data }, 'https://player.hesedvid.com');}
// Example commandssendPlayerCommand('play');sendPlayerCommand('pause');sendPlayerCommand('setVolume', { volume: 0.5 });sendPlayerCommand('seekTo', { time: 120 }); // Seek to 2 minutesIntegration Examples
WordPress Shortcode
function hesedvid_player_shortcode($atts) { $atts = shortcode_atts([ 'video_id' => '', 'width' => '800', 'height' => '450', 'autoplay' => 'false', 'muted' => 'false', 'theme' => 'auto', 'branding' => 'true' ], $atts);
if (empty($atts['video_id'])) { return '<p>Error: Video ID required</p>'; }
$params = []; if ($atts['autoplay'] === 'true') $params[] = 'autoplay=true'; if ($atts['muted'] === 'true') $params[] = 'muted=true'; if ($atts['theme'] !== 'auto') $params[] = 'theme=' . $atts['theme']; if ($atts['branding'] === 'false') $params[] = 'branding=false';
$queryString = implode('&', $params); $src = $queryString ? "https://player.hesedvid.com/{$atts['video_id']}?{$queryString}" : "https://player.hesedvid.com/{$atts['video_id']}";
return sprintf( '<iframe src="%s" width="%s" height="%s" frameborder="0" allowfullscreen></iframe>', esc_url($src), esc_attr($atts['width']), esc_attr($atts['height']) );}add_shortcode('hesedvid_player', 'hesedvid_player_shortcode');
// Usage: [hesedvid_player video_id="pubvid_AbCdEf" width="800" height="450" theme="dark"]React Hook
import { useState, useEffect, useRef } from 'react';
const useHesedVidPlayer = (videoId, options = {}) => { const iframeRef = useRef(null); const [playerState, setPlayerState] = useState({ isReady: false, isPlaying: false, currentTime: 0, duration: 0, volume: 1 });
useEffect(() => { const handleMessage = (event) => { if (event.origin !== 'https://player.hesedvid.com') return;
const { type, ...data } = event.data;
switch (type) { case 'playerReady': setPlayerState(prev => ({ ...prev, isReady: true })); break; case 'play': setPlayerState(prev => ({ ...prev, isPlaying: true })); break; case 'pause': setPlayerState(prev => ({ ...prev, isPlaying: false })); break; case 'timeUpdate': setPlayerState(prev => ({ ...prev, currentTime: data.currentTime })); break; case 'durationChange': setPlayerState(prev => ({ ...prev, duration: data.duration })); break; case 'volumeChange': setPlayerState(prev => ({ ...prev, volume: data.volume })); break; } };
window.addEventListener('message', handleMessage); return () => window.removeEventListener('message', handleMessage); }, []);
const sendCommand = (command, data = {}) => { if (iframeRef.current?.contentWindow) { iframeRef.current.contentWindow.postMessage({ type: command, ...data }, 'https://player.hesedvid.com'); } };
const playerUrl = (() => { const params = new URLSearchParams(); if (options.autoplay) params.append('autoplay', 'true'); if (options.muted) params.append('muted', 'true'); if (options.theme) params.append('theme', options.theme); if (options.branding === false) params.append('branding', 'false');
const queryString = params.toString(); return queryString ? `https://player.hesedvid.com/${videoId}?${queryString}` : `https://player.hesedvid.com/${videoId}`; })();
return { playerUrl, playerState, sendCommand, iframeRef };};
// Usageconst MyVideoComponent = ({ videoId }) => { const { playerUrl, playerState, sendCommand, iframeRef } = useHesedVidPlayer(videoId, { theme: 'dark', branding: false });
return ( <div> <iframe ref={iframeRef} src={playerUrl} width="800" height="450" frameBorder="0" allowFullScreen /> <div> <button onClick={() => sendCommand('play')}>Play</button> <button onClick={() => sendCommand('pause')}>Pause</button> <p>Status: {playerState.isPlaying ? 'Playing' : 'Paused'}</p> <p>Time: {Math.floor(playerState.currentTime)}s</p> </div> </div> );};Security Considerations
Content Security Policy (CSP)
If you’re using CSP headers, add the HesedVid player domain to your policy:
<meta http-equiv="Content-Security-Policy" content="frame-src https://player.hesedvid.com;">Origin Verification
Always verify the message origin when listening for player events:
window.addEventListener('message', function(event) { // Only accept messages from HesedVid player if (event.origin !== 'https://player.hesedvid.com') { return; }
// Process message...});Best Practices
Responsive Design
Always use responsive containers for the player:
.video-container { position: relative; width: 100%; height: 0; padding-bottom: 56.25%; /* 16:9 aspect ratio */}
.video-container iframe { position: absolute; top: 0; left: 0; width: 100%; height: 100%;}Performance Optimization
// Lazy load the playerconst observer = new IntersectionObserver((entries) => { entries.forEach(entry => { if (entry.isIntersecting) { const iframe = entry.target; iframe.src = iframe.dataset.src; observer.unobserve(iframe); } });});
document.querySelectorAll('[data-src]').forEach(iframe => { observer.observe(iframe);});Error Handling
// Handle player errorswindow.addEventListener('message', function(event) { if (event.origin !== 'https://player.hesedvid.com') return;
if (event.data.type === 'error') { console.error('Player error:', event.data.error); // Show fallback content or error message }});Troubleshooting
Common Issues
| Issue | Cause | Solution |
|---|---|---|
| Player not loading | Invalid video ID | Verify the video exists and is public |
| Controls not working | CSP blocking | Add https://player.hesedvid.com to frame-src |
| Events not firing | Origin mismatch | Verify PostMessage origin check |
| Responsive issues | Fixed dimensions | Use responsive container with padding-bottom |
Debug Mode
Enable debug logging by adding debug=true to the player URL:
<iframe src="https://player.hesedvid.com/v1/private/pubvid_AbCdEf/master.m3u8?debug=true"></iframe>This will log additional information to the browser console for troubleshooting.
Rate Limits
| Operation | Limit | Window |
|---|---|---|
| Player loads | 1000 requests | 1 hour |
| Event messages | 10,000 messages | 1 hour |
Tip
The HesedVid player automatically handles video quality selection and adaptive bitrate streaming for optimal viewing experience across all devices.
Caution
Always verify the message origin when using the PostMessage API to prevent security vulnerabilities.