# MediaBlaster Documentation — Full Context Generated from the current files in content/docs. MediaBlaster uses WordPress as the media backend and connects that content to app templates. The Roku Launch Kit is the only app template currently available. Documentation index: https://www.mediablaster.io/docs ## App Config URL: https://www.mediablaster.io/docs/app-config Category: App Config Status: available Product: Roku Launch Kit Summary: Platform-specific app behavior, branding, layout, and feature visibility for connected TV and mobile clients. # App Config **Location:** MediaBlaster → **App Config** → **App Settings** tab Configure how connected apps (starting with the MediaBlaster Roku app) behave, look, and navigate. Settings are stored in WordPress and served publicly to clients via the REST config endpoint. This is **not** API discovery — the app must already know your WordPress site URL to request config. Do not store `apiBaseUrl`, `apiOrigin`, secrets, or private credentials here. ## Platform tabs | Tab | Status | |-----|--------| | **App Settings** (`platform=roku`) | Available | | Mobile, Google TV, Fire TV, Apple TV | Planned — same page will gain additional tabs | ## Sections (App Settings tab) | Section | Purpose | |---------|---------| | **General** | App name, debug mode | | **Content Availability** | VOD, movies, series, categories, search, continue watching | | **Branding** | Colors, fallback images, card/poster aspect ratios | | **Links** | Support and privacy URLs | | **Sidebar** | Sidebar visibility and widths | | **Navigation Features** | Which destinations appear in app navigation (`features` object) | | **Labels** | Custom UI labels (`labels` object) | | **Homepage Layout** | Home screen layout toggles (`layout` object) | | **Home Tag Rows** | Tag-based home row settings (`homeTagRows` object) | | **Boot** | Startup behavior (`boot` object) | | **REST Endpoint** | Read-only display of the public config URL | Each field includes inline help text under its label. Section titles include a short description. ## REST endpoint ``` GET /wp-json/mediablaster/v3/config?platform=roku ``` - Public, read-only (no authentication required) - Default `platform` query value: `roku` - Unsupported platform → `400 mediablaster_invalid_platform` See [REST API — App Config](rest-api-app-config.md) for the response shape. **Not the same as** `GET /app/config` — that route returns subscription/Stripe client configuration when the subscriptions module and REST API are enabled. See [Subscriptions and Apps API](rest-api-subscriptions.md). ## Defaults and saving - If nothing has been saved, the endpoint returns built-in Roku defaults immediately. - `homeRows` is always `[]` in v1 (no admin UI yet). ## Related guides - [REST API — App Config](rest-api-app-config.md) - [REST API Overview](rest-api-overview.md) - [Getting Started](getting-started.md) ## Captions, Trickplay, and Advertising URL: https://www.mediablaster.io/docs/metabox-captions-trickplay-ads Category: Content editor Summary: Closed captions, BIF trickplay files, validity dates, and per-video ad breaks. # Captions, Trickplay, and Advertising Metaboxes These metaboxes appear on video posts when **Enable Legacy Controls** (Legacy Controls section on General Settings) and the specific Meta Controls sub-options are on. See [General Settings → Legacy Controls](general-settings.md#legacy-controls). ## Closed Captions / Subtitles **Metabox:** Closed Captions/Subtitles Add repeatable caption tracks: | Field | Description | |-------|-------------| | **File URI** | URL to `.vtt` (WebVTT) or `.srt` file. WebVTT works on Roku and HTML5; SRT is Roku-only. | | **Language** | BCP 47 language code (e.g. `en`, `es`). | | **Type** | CLOSED_CAPTION or SUBTITLE | Convert SRT to VTT with online tools if needed for cross-platform support. ## Trickplay (deprecated) **Metabox:** Trickplay — **Deprecated in 3.0.0** BIF trickplay files enable scrub preview thumbnails on Roku: | Field | Description | |-------|-------------| | **BIF file URI** | URL to `.bif` file | | **BIF definition** | HD or FHD resolution | Avoid new BIF workflows unless maintaining legacy Roku channels. ## Advanced Controls **Metabox:** Advanced Controls | Field | Description | |-------|-------------| | **Validity start date** | Content available from this date | | **Validity end date** | Content expires after this date | Useful for licensed content windows and live-event replays. ## Advertising Controls **Metabox:** Advertising Controls (not shown on Series posts) Configure per-video ad breaks when feed ad type is **Scheduled** or **Scheduled w/ Automatic Fallback** (from prior configuration or JSON import). | Field | Description | |-------|-------------| | **Ad breaks** | Repeatable cue points (time offsets) | | **Custom mid-roll timer** | Override default mid-roll interval for automatic modes | ## Enabling these metaboxes 1. **General Settings → Enable Legacy Controls** — on 2. Enable the specific control: Subtitles, Trickplay, Advanced, or Advertising ## Related guides - [General Settings](general-settings.md) ## Series and Episodes URL: https://www.mediablaster.io/docs/metabox-series-episodes Category: Content editor Summary: Configure series containers, seasons, episode numbers, and playlists. # Series and Episodes MediaBlaster supports episodic content through **Series** and **Episodes** custom post types. ## Series post type **Location:** WP Admin → **Series** Each series post represents a show or collection. The **Series Data** metabox includes: | Field | Description | |-------|-------------| | **Series type** | Genre/format classification (e.g. episodic, documentary). | | **Release date** | Original or premiere date for feed metadata. | | **Attached episodes playlist** | Ordered list of episode posts belonging to this series. | | **Series thumbnail** | Artwork for series rows on Roku and web. | | **Genres** | Browse metadata for the series. | Attach episodes using the playlist/attached posts control — order here determines episode sequence in feeds. ## Episodes post type **Location:** WP Admin → **Episodes** Each episode is a video post with standard [Video Data](metabox-video-data.md) plus sidebar fields: | Field | Description | |-------|-------------| | **Season number** | Season index (e.g. 1, 2). | | **Episode number** | Episode index within the season. | ## Enabling series Turn on **Enable Series** under [General Settings](general-settings.md). Both Series and Episodes post types register together. ## Feed behavior When series are enabled in your feed configuration, the JSON feed at `/wp-json/tv/roku/` outputs a `series` array with nested seasons and episodes referencing episode content IDs and stream URLs. View or download the feed under [Import and Export](import-export.md). ## Tips - Publish episodes before attaching them to a series playlist. - Use consistent season/episode numbering — gaps may confuse Roku season browsers. - Tag episodes for feed category recipes when using tag-based categories (configured via JSON import). ## Related guides - [Video Data metabox](metabox-video-data.md) - [Import and Export](import-export.md) ## Subscription Access Metabox URL: https://www.mediablaster.io/docs/metabox-subscription-access Category: Content editor Summary: Gate individual videos by tier, access group, trials, and feed visibility. # Subscription Access Metabox **Location:** Post editor sidebar, below Featured Image, on premium-capable post types when subscriptions are enabled Control who can watch each video and how unauthorized viewers experience locked content. ## Prerequisites - Subscriptions enabled via `WPST_SUBSCRIPTIONS_ENABLED` in `wp-config.php` (see [General Settings](general-settings.md)) ## Fields | Field | Description | |-------|-------------| | **Access level** | Free, any subscriber, specific tier, or specific access group | | **Required tier** | When access level is tier-specific, choose the plan | | **Required access group** | When access level is group-specific, choose the bundle | | **Allow trial access** | Let trialing subscribers watch this item | | **Hide from public feeds** | Exclude from JSON feeds even if published | | **Unauthorized behavior** | Show locked message vs hide completely (overrides site default) | Defaults for new posts come from [Subscriptions General](subscriptions-general.md). ## Feed and player behavior - `[mediablaster_player]` and `[tv-video-player]` respect entitlements — non-subscribers see a locked player overlay (poster + subscribe/login message) or nothing when **Hide completely** is configured. - Playable video URLs are never output in HTML when access is denied. - Public Roku feed is unchanged unless **Apply subscription rules to legacy IPTV feeds** is enabled globally. ## Workflow example 1. Create a **Premium** access group with sports content. 2. Link the group to a **Sports** tier. 3. On each sports video, set access level to that group or tier. 4. Subscribers on the Sports tier can play; others see the locked state. ## Related guides - [Subscriptions Overview](subscriptions-overview.md) - [Access Groups](subscriptions-access-groups.md) - [Shortcodes](shortcodes.md) ## Video Data Metabox URL: https://www.mediablaster.io/docs/metabox-video-data Category: Content editor Summary: Media URL, duration, quality, genres, and parental rating on video posts. # Video Data Metabox **Location:** Post editor on Movies, Short Videos, and Episodes The **Video Data** metabox contains required technical metadata for IPTV feeds and the HTML5 player. ## Fields | Field | Description | |-------|-------------| | **Media URL** | Direct HLS (`.m3u8`) or MP4 URL. YouTube URLs are not supported. | | **Duration** | Length in seconds — used in feed JSON and players. | | **Video Format** | Stream type indicator (e.g. HLS, MP4). | | **Quality** | Resolution label (e.g. HD, FHD, 4K). | | **Genres** | Comma-separated or selected genres for browse/filter metadata. | | **Parental Rating** | Content rating for platform compliance (e.g. G, PG, TV-14). | ## Best practices - Use CDN or Vimeo HLS URLs that allow direct playback on Roku and HTML5. - Match duration to actual file length — incorrect values break trickplay and ad scheduling. - Set featured images separately — they appear as thumbnails in feeds. ## Vimeo import When **Enable Vimeo Integration** is on in General Settings, use the [Vimeo metabox](metabox-vimeo-import.md) **Load Video Data** button to populate URL, duration, quality, tags, and optionally title/description. ## Feed output Values save to `rovidx_smarttv_*` post meta and appear in the [Content REST API](rest-api-content.md) as the `media`, `taxonomy`, and related fields. Missing Media URL or Duration may cause playback or feed issues on devices. ## Related guides - [Getting Started](getting-started.md) - [Series and Episodes](metabox-series-episodes.md) - [Shortcodes](shortcodes.md) ## Vimeo Metabox URL: https://www.mediablaster.io/docs/metabox-vimeo-import Category: Content editor Summary: Import single videos from Vimeo and optional upload to Vimeo. # Vimeo Metabox **Location:** Post editor on enabled video post types (Movies, Short Videos, Episodes) The **Vimeo** metabox connects individual posts to Vimeo Pro/Business videos. ## Vimeo URL field Paste a Vimeo video URL (e.g. `https://vimeo.com/123456789`) into **Vimeo URL**, then click **Load Video Data**. When [Vimeo is connected](integrations-vimeo-oauth.md), MediaBlaster fetches: - HLS stream URL → **Media URL** - Duration, quality, format - Tags and description (when [Vimeo Settings](vimeo-settings.md) allow) - Title (when title import is enabled) - Featured image thumbnail Imported values populate `rovidx_smarttv_*` meta used by Roku feeds. ## Upload to Vimeo When **Enable Vimeo Uploads** is on and OAuth is connected, an **Upload to Vimeo** panel appears: 1. Select a local video file 2. Start upload — progress polls via AJAX 3. On completion, the Vimeo URL and metadata can be loaded into the post Requires sufficient Vimeo account storage and upload API permissions. ## Prerequisites - **Enable Vimeo Integration** on [General Settings](general-settings.md) - [Integrations (Vimeo OAuth)](integrations-vimeo-oauth.md) completed - Import preferences under [Vimeo Settings](vimeo-settings.md) ## Bulk alternative For many videos, use [Vimeo Mass Import](vimeo-mass-import.md) instead of per-post loading. ## Related guides - [Video Data metabox](metabox-video-data.md) - [Vimeo Settings](vimeo-settings.md) ## MediaBlaster Player URL: https://www.mediablaster.io/docs/mediablaster-player Category: Front-end Summary: Embed the MediaBlaster streaming player with Video.js, shortcode, Gutenberg block, Elementor widget, and skins. # MediaBlaster Player The MediaBlaster player embeds video on WordPress pages and posts. **Video.js** is the default playback engine with a safe **native HTML5 fallback**, multi-source HLS/DASH/MP4 support, caption/chapter/thumbnail tracks, and subscription-aware locked states. The shortcode, Gutenberg block, and Elementor widget all use the same player. Locked or premium content never exposes playable source URLs in HTML when access is denied. ## Using the MediaBlaster Player shortcode ``` [mediablaster_player] ``` ## Legacy shortcode (still supported) ``` [tv-video-player] ``` Both shortcodes use the same renderer. New sites should prefer `[mediablaster_player]`. Example with skin: ``` [mediablaster_player id="123" skin="streaming"] ``` ## Using the MediaBlaster Player Gutenberg block 1. In the block editor, click **+** and search for **MediaBlaster Player** (category: **Media**). 2. Insert the block and open the sidebar panels: **Video Source**, **Player Display**, **Playback Options**, **Tracks**, **Advanced**. 3. Choose a **Video Post ID** (search or numeric ID). The block **imports** HLS/MP4, poster, and track URLs from that post’s MediaBlaster meta into the sidebar (editable). You can also enter direct URLs manually. 4. Publish — the player appears on the live page. Imported HLS/MP4 URLs in the sidebar are **for reference only** when a **Video Post ID** is set. The frontend always loads **fresh URLs from that video post** on each page view (same as the shortcode). This matters for Vimeo and other signed CDN URLs that expire. **Use URL fields instead of post meta** (Advanced) applies only when **no video post** is selected (manual URL mode). The toggle is disabled when a post ID is set. If URL fields stay empty after selecting a post, reload the editor or re-select the video — playback still works from post meta when only **Video Post ID** is set. The editor shows a live preview when a source is configured. Subscription and source resolution behave the same as on the published page. ## Using the MediaBlaster Player Elementor widget Requires [Elementor](https://elementor.com/) (Elementor Pro not required). 1. Edit a page with Elementor. 2. Search the widget panel for **MediaBlaster Player** (category **MediaBlaster**). 3. Configure **Source mode**: - **Current Post** — uses the post ID of the page being viewed. On **Theme Builder** templates (e.g. single `movies`), set the sample post under the template **Preview Settings** (gear → Preview Settings → choose a movie); the editor canvas uses that preview post, not the `elementor_library` template post itself. - **Select Post** — pick a video from the dropdown or enter a Post ID. - **Direct URLs** — HLS/DASH/MP4 fields only (optional Post ID for poster/meta fallback). 4. Adjust display, playback, and track settings in the remaining sections. **Editor preview:** The Elementor canvas shows the **same live player** as the published page, not a text-only placeholder. If no source is configured yet, a dashed hint box explains what to set. Subscription-locked videos show the locked state in the editor too. Example: drag **MediaBlaster Player** onto the page, set **Current Post** on a single movie template, or **Select Post** with a specific video ID. ## Choosing a source | Method | Best for | |--------|----------| | Post ID (shortcode `id`, block **Video Post ID**, Elementor **Select Post**) | Videos with MediaBlaster meta (`rovidx_smarttv_URL`, format, captions, BIF) | | Direct URLs | External streams, landing pages without a video CPT post | | Current post context | `[mediablaster_player]` with no `id` on a movie/episode singular template | URL priority when overrides are set: `hls` → `dash` → `mp4_1080`–`360` → `url` → `mp4` → post meta. See [Source resolution](#source-resolution) below. Enabled video post types depend on **MediaBlaster → General Settings** (movies, short videos, episodes). The block editor searches these types via AJAX; Elementor lists up to 50 recent published videos per type. ## Selecting a player skin | Skin | Use case | |------|----------| | `default` | General site embeds | | `streaming` | TV-style layouts | | `creator` | Creator-focused pages | Set via shortcode `skin="streaming"`, block **Player Display → Skin**, or Elementor **Player Display → Skin**. ## Adding captions - **From post meta:** use default behavior (`captions="true"` on shortcode, or leave caption URL empty in block/widget). - **Override with WebVTT:** `caption="https://…/en.vtt"` plus `caption_label` and `caption_lang`. - **Subtitles track:** `subtitles` URL with `subtitles_label` / `subtitles_lang`. ## Adding chapters - **Boolean (default):** `chapters="true"` loads chapter behavior from post meta when available. - **WebVTT URL:** `chapters="https://…/chapters.vtt"` with optional `chapters_label` and `chapters_lang`. Configure in the block/widget **Tracks** panel or shortcode attributes. ## Adding thumbnail/storyboard tracks - **BIF from meta:** `thumbnails="true"` (default) loads `rovidx_smarttv_bif` when present. - **WebVTT storyboard:** `thumbnails="https://…/thumbnails.vtt"`. BIF scrubber UI on the progress bar is not implemented yet; metadata is stored for future use. ## Autoplay and muted behavior Most browsers **block autoplay with sound**. For reliable autoplay, enable **Muted** as well as **Autoplay**. The Gutenberg block shows a warning in the sidebar when autoplay is on and muted is off. Elementor includes the same guidance in control help text. ## Native fallback mode Force native HTML5 (skip Video.js): ``` [mediablaster_player player_engine="native"] ``` Or set **Player engine → Native HTML5** in the block or Elementor widget. If Video.js is unavailable, the player falls back automatically. ## Basic examples Current post context: ``` [mediablaster_player] ``` Specific video post: ``` [mediablaster_player id="123"] ``` Direct MP4 URL: ``` [mediablaster_player mp4="https://example.com/video.mp4"] ``` HLS stream: ``` [mediablaster_player hls="https://example.com/master.m3u8"] ``` DASH stream: ``` [mediablaster_player dash="https://example.com/manifest.mpd"] ``` Multiple MP4 qualities: ``` [mediablaster_player mp4_1080="https://example.com/video-1080.mp4" mp4_720="https://example.com/video-720.mp4" mp4_480="https://example.com/video-480.mp4"] ``` Poster override: ``` [mediablaster_player id="123" poster="https://example.com/poster.jpg"] ``` Autoplay (requires muted for most browsers): ``` [mediablaster_player id="123" autoplay="true" muted="true"] ``` Vertical video: ``` [mediablaster_player id="123" aspect_ratio="9:16"] ``` Captions (WebVTT): ``` [mediablaster_player caption="https://example.com/captions.vtt" caption_label="English" caption_lang="en"] ``` Subtitles: ``` [mediablaster_player subtitles="https://example.com/es.vtt" subtitles_label="Spanish" subtitles_lang="es"] ``` Chapters (WebVTT): ``` [mediablaster_player chapters="https://example.com/chapters.vtt" chapters_label="Chapters" chapters_lang="en"] ``` Thumbnail/storyboard VTT: ``` [mediablaster_player thumbnails="https://example.com/thumbnails.vtt"] ``` Legacy BIF trickplay URL (stored for future scrubber UI): ``` [tv-video-player bif="https://example.com/storyboard.bif"] ``` Player skins: ``` [mediablaster_player skin="streaming"] [mediablaster_player skin="creator"] ``` Native HTML5 fallback (skip Video.js): ``` [mediablaster_player player_engine="native"] ``` ## Player engine Default engine: **videojs**. - Video.js loads only when a player is rendered on the page (not globally). - If bundled Video.js files are missing, or another plugin already registered Video.js, the player adapts automatically. - If Video.js is unavailable, playback falls back to native HTML5 without breaking the page. Bundled assets live at `public/vendor/videojs/` inside the plugin. See that folder’s README for upgrade instructions. ## Supported attributes | Attribute | Default | Description | |-----------|---------|-------------| | `id` | current post | Video post ID | | `player_engine` | `videojs` | `videojs` or `native` | | `hls` | — | HLS master URL (`.m3u8`) | | `dash` | — | DASH manifest URL (`.mpd`) | | `mp4_1080` | — | 1080p MP4 URL | | `mp4_720` | — | 720p MP4 URL | | `mp4_480` | — | 480p MP4 URL | | `mp4_360` | — | 360p MP4 URL | | `url` | — | Generic video URL override | | `mp4` | — | MP4 URL override | | `type` | auto | Force format: `hls`, `mp4`, `dash`, etc. | | `poster` | featured image | Poster image URL | | `max_width` | `1920px` | CSS max-width | | `aspect_ratio` | `16:9` | `16:9`, `4:3`, `1:1`, `9:16`, `21:9` | | `skin` | `default` | `default`, `streaming`, `creator` | | `controls` | `true` | Show player controls | | `preload` | `metadata` | `none`, `metadata`, `auto` | | `autoplay` | `false` | Autoplay when allowed | | `loop` | `false` | Loop playback | | `muted` | `false` | Mute audio | | `playsinline` | `true` | Mobile inline playback | | `start_time` | `0` | Seek to seconds on load | | `class` | — | Extra CSS classes | | `bif` | — | Legacy BIF URL or VTT storyboard alias | | `captions` | `true` | Load caption tracks from post meta | | `caption` | — | Single captions VTT URL | | `caption_label` | English | Captions track label | | `caption_lang` | `en` | Captions track language | | `subtitles` | — | Single subtitles VTT URL | | `subtitles_label` | English | Subtitles track label | | `subtitles_lang` | `en` | Subtitles track language | | `captions_json` | — | JSON array of multiple caption/subtitle tracks | | `chapters` | `true` | Boolean flag, or chapters VTT URL | | `chapters_label` | Chapters | Chapters track label | | `chapters_lang` | `en` | Chapters track language | | `thumbnails` | `true` | Boolean flag for BIF meta, or thumbnails VTT URL | | `thumbnail_label` | Thumbnails | Thumbnail metadata track label | | `resume` | `false` | Reserved for future resume watching | | `autoplay_next` | `false` | Reserved for future playlist autoplay | | `locked_behavior` | `overlay` | `overlay` or `message` when access denied | ### Dual-mode attributes - **`thumbnails`**: `true`/`false` controls BIF meta loading; a URL value sets a WebVTT metadata track. - **`chapters`**: `true`/`false` sets the chapters feature flag; a URL value adds a WebVTT chapters track. - **`captions`**: `false` disables all caption/subtitle output including post meta. ## Source resolution URL priority: 1. Shortcode `hls` 2. Shortcode `dash` 3. Shortcode `mp4_1080`, `mp4_720`, `mp4_480`, `mp4_360` 4. Shortcode `url` 5. Shortcode `mp4` 6. Post meta `rovidx_smarttv_URL` 7. Fire Creator add-on MP4 meta (when active) Format detection uses explicit args, post meta `rovidx_smarttv_format`, or URL extension (`.m3u8`, `.mpd`, `.mp4`). For HLS (`.m3u8`), the player follows master-playlist redirects server-side before rendering (common for Vimeo and other CDNs). This ensures variant playlists and segments load from the CDN origin with proper CORS instead of failing with a perpetual spinner. Captions load from post meta `rovidx_smarttv_cc` when `captions="true"`. BIF trickplay loads from post meta `rovidx_smarttv_bif` when `thumbnails="true"` (boolean mode). ## Subscription access When subscriptions are enabled, the player checks entitlements before outputting playable sources. - **Show locked** — Branded overlay with poster; no video URL in markup - **Hide completely** — Empty output (no player rendered) - Use `locked_behavior="message"` for legacy plain-text locked message See [Subscription Access Metabox](metabox-subscription-access.md). ## Troubleshooting ### Block shows poster but no play button or controls (shortcode works) **Typical signs:** HLS or segments may load in the Network tab; no JavaScript errors; Video.js poster visible; no big play icon or control bar. **Cause:** Video.js can end up in `vjs-controls-disabled` when ingesting a `