Add shoppable video

FastPix Player now supports shoppable video themes, giving you the ability to embed interactive shopping experiences directly inside your videos. Instead of just watching, viewers can click, explore, and even purchase products while engaging with your content.

There are two themes you can choose from, depending on the type of video experience you want to build:

  • Shoppable video player - a full-featured player with a product sidebar, catalog browsing, and timeline-aware product activations.
  • Shoppable shorts - a lightweight, mobile-first option optimized for single products and social video formats.

Both themes allow you to add clickable products, hotspots, and calls-to-action seamlessly. The main difference lies in how product data is configured and displayed.


Theme behavior

  • shoppable-video-player expects product data passed programmatically through the addShoppableData() method. Any product-link attribute you set will be ignored.
  • shoppable-shorts only uses the product-link attribute. No product data configuration is needed or processed.

Shoppable video player theme

A full, interactive shopping experience with an expandable sidebar and detailed product catalog. This theme is best suited for multi-product or long-form content where viewers can browse items while watching.

FeatureDescription
Interactive Product SidebarExpandable panel listing products with thumbnails, names, and descriptions.
Product Hover OverlaysText overlays appear when hovering over sidebar items, showing extra product info.
Image Swap on HoverSwap product images (e.g., different angles or colors) when hovered.
Clickable HotspotsInteractive markers on the video timeline that link directly to products.
Post-Play Product OverlayProduct carousel appears once the video ends, driving continued engagement.
Auto Open/Close SidebarSidebar can open automatically on play and auto-close after a set duration.
Product Click ActionsClicking a product can seek the video to a timestamp or open an external purchase link.
Time-Based Product ActivationProducts activate and deactivate based on video timestamps, highlighting the right item at the right time.

Use cases

  • E-commerce showcases: Display multiple products with detailed info and links.
  • Fashion & lifestyle content: Highlight clothing, accessories, or styling products with hover effects.
  • Educational content: Reference books, tools, or course material mentioned in video.
  • Long-form content: Manage many products across extended timelines with an organized sidebar.
  • Product demos: Highlight specific items precisely at the moment they’re being demonstrated.


Shoppable shorts theme

A simplified, call-to-action driven theme for quick, single-product experiences. Designed for mobile-first and social platforms.

FeatureDescription
Single External Link IntegrationOne-click setup — opens a specified URL when the cart button is tapped.
Cart ButtonProminent “shop” button optimized for mobile UX.
Mobile-First DesignUI elements tailored for small screens and touch interactions.
Minimal UI FootprintClean, unobtrusive design that keeps focus on the video.
No Complex SetupRequires only the product-link attribute, no extra JavaScript.
Social Media OptimizedPerfect for TikTok, Instagram Reels, and YouTube Shorts.

Use cases

  • Social media shorts: Quick promos across TikTok, Instagram, YouTube Shorts.
  • Mobile-first campaigns: Videos consumed primarily on phones.
  • Single-product promos: Focused campaigns where one link drives conversions.
  • Fast purchase flows: Low-friction buying experiences.
  • Simple CTA campaigns: “Tap to shop” videos pointing to a single destination.
  • Influencer marketing: Creators linking directly to sponsored products.

Theme comparison

FeatureShoppable Video PlayerShoppable Shorts
Product CatalogFull sidebar with multiple productsSingle external link only
ConfigurationRequires addShoppableData() with product arrayOnly needs product-link attribute
HotspotsAvailable (timeline markers)Not available
Hover EffectsOverlays and image swapsNot available
Post-Play OverlayCarousel shown after video endsNot available
Click ActionsSeek video or open linkExternal URL only
Best ForMultiple products, rich experiencesSingle product, quick CTAs
Content LengthLong-form videoShort-form video
PlatformWeb applications, detailed showcasesSocial media, mobile-first

Setting up shoppable video player

This theme is the full-featured option, designed for multi-product or catalog-style experiences. It requires a little configuration, but gives you far more control over how products are displayed and how they interact with the video timeline.


1. Basic setup

At the most basic level, you only need to include the FastPix player with the correct theme and a playback ID:

<fastpix-player  
  theme="shoppable-video-player" 
  playback-id="your-playback-id"> 
</fastpix-player> 

This creates a player with shoppable capability, but it won’t show any products yet. To make the sidebar and hotspots come alive, you’ll need to pass product data to the player.


2. Add product data

To load product information, use the addShoppableData() method. This method expects a JSON configuration that defines both sidebar behavior and the product catalog.

const player = document.querySelector('fastpix-player'); 
 
const cartData = { 
  productSidebarConfig: { 
    startState: "closed",        // "closed" or "openOnPlay" 
    autoClose: 4,               // Auto-close after 4 seconds 
    showPostPlayOverlay: true   // Show overlay when video ends 
  }, 
  products: [ 
    { 
      id: 1,                    // Unique product ID 
      name: "Product Name",     // Product display name 
      thumbnail: "https://example.com/product.jpg",  // Product image URL 
      description: "Product description",  // Optional description 
      startTime: 0,             // When product becomes active (seconds) 
      endTime: 5,               // When product becomes inactive (seconds) 
       
      // Click action configuration 
      onProductClick: { 
        type: "seek",           // "seek" or "openLink" 
        waitTillPause: 6,       // Wait 6 seconds then play 
        params: { 
          seekTime: 5           // Seek to 5 seconds 
        } 
      }, 
       
      // Hover action configuration 
      onProductHover: { 
        type: "overlay",        // "overlay" or "swap" 
        params: { 
          description: "Product description appears on hover" 
        } 
      }, 
       
      // Hotspot markers (optional) 
      markers: [ 
        { 
          x: 175,               // X position as percentage (0-100) 
          y: 60,                // Y position as percentage (0-100) 
          tooltipPosition: "left",  // "top", "bottom", "left", "right" 
          link: "https://store.com/product"  // URL when hotspot clicked 
        } 
      ] 
    } 
  ] 
}; 
 
player.addShoppableData(cartData); 
 

With this setup:

  • The sidebar starts closed but opens when playback begins.
  • Products appear only during the times you specify with startTime and endTime.
  • Clicking a product either seeks the video or opens an external link, depending on configuration.
  • Hovering over a product reveals extra details or swaps the product image.
  • Optional hotspots can be placed directly on the video itself.

Setting up shoppable shorts

This theme is the lightweight option, optimized for single products and mobile-first consumption (e.g., TikTok, Instagram Reels). Unlike shoppable video player, it doesn’t need a product catalog. Instead, it only requires a single link.


Basic setup

Add the FastPix player with the theme set to shoppable-shorts, plus a product-link attribute. When the video plays, a cart button will automatically appear. Tapping it redirects viewers to the specified product link.


<fastpix-player  
  theme="shoppable-shorts" 
  product-link="https://your-store.com" 
  playback-id="your-playback-id"> 
</fastpix-player> 

PLEASE NOTE

For shoppable-shorts, only the product-link attribute is required. No additional JavaScript configuration needed.


Summary of setup differences


shoppable-video-player:

  • Requires calling addShoppableData(config) with a product array.
  • Supports multiple products, sidebars, overlays, hotspots, and time-based activation.
  • Ignores the product-link attribute.

shoppable-shorts:

  • Requires only the product-link attribute.
  • Supports a single product with a clean “shop” button.
  • Ignores product data configuration.

JSON structure explained

The data is structured as a JSON object with two main parts:

  1. productSidebarConfig - defines how the sidebar behaves (when it opens, closes, and whether overlays appear).
  2. products - an array of product objects, each representing a clickable product inside your video.

Here’s the complete structure:

{ 
  productSidebarConfig: { 
    startState: "closed",        // Sidebar initial state 
    autoClose: 4,               // Auto-close timer (seconds) 
    showPostPlayOverlay: true   // Show overlay when video ends 
  }, 
  products: [ 
    { 
      id: 1,                    // Product ID (number or string) 
      name: "Product Name",     // Product display name 
      thumbnail: "image-url",   // Product image URL 
      description: "Description", // Optional description 
      startTime: 0,             // Product active start time (seconds) 
      endTime: 5,               // Product active end time (seconds) 
       
      onProductClick: {         // Click action (optional) 
        type: "seek",           // Action type 
        waitTillPause: 6,       // Wait time before playing 
        params: {               // Action parameters 
          seekTime: 5           // Target time for seek 
        } 
      }, 
       
      onProductHover: {         // Hover action (optional) 
        type: "overlay",        // Action type 
        params: {               // Action parameters 
          description: "Text to show on hover" 
        } 
      }, 
       
      markers: [                // Hotspot markers (optional) 
        { 
          x: 175,               // X position (0-100%) 
          y: 60,                // Y position (0-100%) 
          tooltipPosition: "left", // Tooltip position 
          link: "url"           // Link when clicked 
        } 
      ] 
    } 
  ] 
} 

Product configuration

Products are defined inside the products array. Each product has required fields (which the player needs to function) and optional fields (to enrich interactivity).

Required fields

FieldTypeDescription
idNumber / StringUnique product identifier, used internally for tracking and analytics.
nameStringProduct display name, shown in sidebar, tooltips, and overlays.
thumbnailStringURL of the product image (appears in sidebar and hover overlays).

Optional fields

FieldTypeDescription
descriptionStringAdditional product details shown in overlays and tooltips.
startTimeNumberTimestamp (in seconds) when product becomes active in the video.
endTimeNumberTimestamp (in seconds) when product becomes inactive.
onProductClickObjectDefines what happens when a product is clicked.
onProductHoverObjectDefines hover behavior (text overlays or image swaps).
markersArrayList of hotspots placed directly on the video (time + position).

Product actions reference

Products can trigger two types of interactivity:

Click actions

Defines what happens when a product is selected in the sidebar or overlay.

Action Type

Description

Parameters

Default Values

"openLink"

Opens an external URL in a new tab.

targetUrl (string) → destination link shouldPause (boolean) → pause video before opening

shouldPause: false

"seek"

Seeks the video to a specific timestamp.

seekTime (number) → target video time waitTillPause (number) → delay before resuming playback


Click action configuration example:

// Open external link with video pause 
onProductClick: { 
  type: "openLink", 
  params: { 
    targetUrl: "https://store.com/product", 
    shouldPause: true 
  } 
} 
 
// Seek to specific time with wait 
onProductClick: { 
  type: "seek", 
  params: { 
    seekTime: 45, 
    waitTillPause: 10 
  } 
} 

Hover actions

Hover actions control what happens when a user moves their mouse over a product in the sidebar.

Action TypeDescriptionParametersRequired
"overlay"Shows a text overlay on hover.description (string) → text to displayRequired
"swap"Switches product image on hover.switchImage (string) → alternative image URLRequired

Hover action configuration example:

// Show text overlay on hover 
onProductHover: { 
  type: "overlay", 
  params: { 
    description: "Premium product with excellent quality" 
  } 
} 
 
// Switch image on hover 
onProductHover: { 
  type: "swap", 
  params: { 
    switchImage: "https://example.com/product-alt-view.jpg" 
  } 
}

Sidebar configuration

The productSidebarConfig object customizes how the sidebar behaves during playback.

PropertyTypeDescriptionDefault ValueOptions
startStateStringWhether sidebar opens automatically when video plays."openOnPlay""closed", "openOnPlay"
autoCloseNumberAuto-close sidebar after X seconds.undefinedAny positive integer
showPostPlayOverlayBooleanShow product carousel after video ends.falsetrue or false

Example:

productSidebarConfig: { 
  startState: "openOnPlay",  // Sidebar opens when video starts  
  autoClose: 30,             // Auto-close after 30 seconds 
  showPostPlayOverlay: true  // Show overlay when video ends 
}

Hotspot marker configuration

Hotspot markers let you place clickable pins directly inside the video frame. These markers can appear at specific times during playback, linking viewers to products or external pages. They’re a powerful way to make your video feel more interactive - imagine a furniture demo where pins appear directly on the chair or table being shown.

Each marker is defined inside the markers array of a product object.


Marker object structure

PropertyTypeRequiredDescriptionDefault Value
xNumberYesHorizontal position of the marker, expressed as a percentage of the video width (0–100).None
yNumberYesVertical position of the marker, expressed as a percentage of the video height (0–100).None
tooltipPositionStringYesDirection of the tooltip relative to the hotspot.None
linkStringYesURL to open when the hotspot is clicked.None

Example:

markers: [ 
  { 
    seekTime: 15,           // Appear at 15 seconds 
    x: 25,                  // 25% from left 
    y: 30,                  // 30% from top 
    tooltipPosition: "bottom", // See below table for tooltip positioning 
    link: "https://store.com/product" 
  } 
]

In this example:

  • A marker appears 15 seconds into the video.
  • It’s positioned at 25% from the left and 30% from the top of the player.
  • When hovered, the tooltip shows up below the marker.
  • Clicking the marker takes the viewer to an external product page.

Tooltip position options

Tooltips help keep the UI intuitive by making it clear what a marker represents without overwhelming the video with too much text.


CSS customization

By default, the shoppable themes follow FastPix’s built-in styles, ensuring the sidebar, buttons, and overlays adapt well across devices. But in most real-world cases, you’ll want the player to match your brand identity.

FastPix Player supports CSS custom properties (variables) that let you tweak the look and feel without digging into the player’s internals.


Available custom properties:

You can apply these variables directly to the <fastpix-player> element in your stylesheet:

fastpix-player { 
  --shoppable-sidebar-width: 30%; 
  --shoppable-sidebar-background-color: rgba(255, 255, 255, 0.75); 
  --accent-color: #ff6b35; 
} 


Events

Beyond displaying products, the shoppable player emits events you can listen for in JavaScript. These events allow you to:

  • Track user interactions (clicks, hovers, replays).
  • Build custom analytics pipelines.
  • Trigger custom UI or backend logic based on how viewers interact with products.

Events are emitted both for sidebar interactions and for the post-play overlay. Some events also indicate sidebar state changes and video lifecycle actions (like replay).


Available events:

EventDescriptionEvent Detail
productHoverTriggered when a user hovers over a product in the sidebar.e.detail.product → object with id, name, thumbnail, etc.
productClickTriggered when a user clicks on a product in the sidebar.e.detail.product
productBarMaxFired when the product sidebar is opened/expanded.No details
productBarMinFired when the product sidebar is closed/minimized.No details
productHoverPostTriggered when hovering over a product in the post-play overlay.e.detail.product
productClickPostTriggered when clicking on a product in the post-play overlay.e.detail.product
replayFired when the video is replayed/restarted.No details

Event usage examples

Listening to product events is straightforward - attach event listeners to the player element:

// Product interaction events (with product data) 
player.addEventListener('productHover', (e) => { 
  console.log('Product hovered:', e.detail.product.name); 
  // Track analytics: product hover in sidebar 
}); 
 
player.addEventListener('productClick', (e) => { 
  console.log('Product clicked:', e.detail.product.id); 
  // Track analytics: product click in sidebar 
}); 
 
// Sidebar state events (no event detail) 
player.addEventListener('productBarMax', () => { 
  console.log('Sidebar opened'); 
  // Track analytics: sidebar opened 
}); 
 
player.addEventListener('productBarMin', () => { 
  console.log('Sidebar closed'); 
  // Track analytics: sidebar closed 
}); 
 
// Post-play overlay events (with product data) 
player.addEventListener('productHoverPost', (e) => { 
  console.log('Post-play hover:', e.detail.product.name); 
  // Track analytics: product hover in post-play overlay 
}); 
 
player.addEventListener('productClickPost', (e) => { 
  console.log('Post-play click:', e.detail.product.id); 
  // Track analytics: product click in post-play overlay 
}); 
 
// Video replay event (no event detail) 
player.addEventListener('replay', () => { 
  console.log('Video replayed'); 
  // Track analytics: video replay 
}); 


Complete example

Here’s a single snippet that wires up the shoppable player, passes product data, customizes CSS, and listens to events.

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <script src="https://cdn.jsdelivr.net/npm/@fastpix/fp-player@latest/dist/player.js"></script>
    <title>FastPix Player</title>
    <style>
        #player-playlist {
            --shoppable-sidebar-width: 30%;
        }
    </style>
</head>
<body>
    <h3>FastPix Player - Shoppable player & Navigation Demo</h3>
    <fastpix-player id="player-playlist" theme="shoppable-video-player"
        playback-id="919ec265-f409-4dd8-ac3d-366181e12e7a" custom-domain="stream.fastpix.app" min-resolution="480p"
        max-resolution="720p">
    </fastpix-player>
    <script>

        // Wait until the custom element is defined 
        customElements.whenDefined('fastpix-player').then(() => {
            const player = document.getElementById('player-playlist');
            const cartData = {// Instead of cartProducts and productSidebarConfig as separate properties, combine them: 
                productSidebarConfig: {
                    startState: "openOnPlay",
                    autoClose: 4,
                    showPostPlayOverlay: true,
                },
                products: [
                    {
                        id: 1,
                        thumbnail:
                            "https://in.zohocommercecdn.com/product-images/JNW+Shajahan+Sofa+Set+Single+Rosewood+1.jpg/431189000086560983/600x600?storefront_domain=www.jfa.in",
                        name: "chair",
                        description: "Description 1",
                        startTime: 0,
                        endTime: 5,
                        markers: [
                            {
                                x: 175,
                                y: 60,
                                tooltipPosition: "left",
                                link: "https://www.jfa.in/products/JNW-Shajahan-Sofa-Set-Single-Rosewood-Dx-Premium-Wooden-Sofa-Set/431189000029424510",
                            },
                        ],
                        onProductClick: {
                            type: "seek",
                            waitTillPause: 6,
                            params: {
                                seekTime: 5,
                            },
                        },
                        onProductHover: {
                            type: "overlay",
                            params: {
                                description: "see this product in the video",
                            },
                        },
                    },
                    {
                        id: 2,
                        thumbnail:
                            "https://in.zohocommercecdn.com/product-images/FDI+Treviso+Sofa+3+Seater+1.jpg/431189000087278412/600x600?storefront_domain=www.jfa.in",
                        name: "Treviso Sofa",
                        description: "Description 1",
                        startTime: 6,
                        endTime: 10,
                        markers: [
                            {
                                x: 60,
                                y: 50,
                                tooltipPosition: "left",
                                link: "https://www.jfa.in/products/aa55d60413/431189000071080281",
                            },
                        ],
                        onProductClick: {
                            type: "seek",
                            waitTillPause: 3,
                            params: {
                                seekTime: 7,
                            },
                        },
                        onProductHover: {
                            type: "overlay",
                            params: {
                                description: "see this product in the video",
                            },
                        },
                    },
                    {
                        id: 3,
                        thumbnail:
                            "https://in.zohocommercecdn.com/product-images/1400x1400-Photoroom+%281%29.jpg/431189000076435150/600x600?storefront_domain=www.jfa.in",
                        name: "Product 2",
                        description: "Description 2",
                        startTime: 11,
                        endTime: 18,
                        onProductClick: {
                            type: "openLink",
                            shouldPause: true,
                            params: {
                                targetUrl:
                                    "https://www.jfa.in/products/guru-ct-01-computer-table-30x18x30-walnut-computer-study-table/431189000070278273",
                            },
                        },
                        onProductHover: {
                            type: "overlay",
                            params: {
                                description: "Click to view the product",
                            },
                        },
                    },
                    {
                        id: 4,
                        thumbnail:
                            "https://in.zohocommercecdn.com/product-images/AMM+Topaz+Plastic+Chair+W+Metal+Leg+and+Seat+Cushion+YellowOffice+Chair+3.jpg/431189000087691668/300x300?storefront_domain=www.jfa.in",
                        name: "AMM Topaz Plastic Chair",
                        description: "Description 3",
                        markers: [
                            {
                                x: 50,
                                y: 50,
                                tooltipPosition: "top",
                                link: "https://www.jfa.in/products/JNW-DT-Heart-Jali-Dining-Table-60X36-Walnut-Dining-Table/431189000029421080",
                            },
                        ],
                        onProductClick: {
                            type: "seek",
                            waitTillPause: 30,
                            params: {
                                seekTime: 32,
                            },
                        },
                        onProductHover: {
                            type: "swap",
                            params: {
                                switchImage:
                                    "https://in.zohocommercecdn.com/product-images/AMM+Topaz+Plastic+Chair+W+Metal+Leg+and+Seat+Cushion+YellowOffice+Chair+1.jpg/431189000087691662/600x600?storefront_domain=www.jfa.in",
                            },
                        },
                    },
                ],
            };

            // Provide your shoppable JSON 
            player.addShoppableData(cartData);

            // Optional: listen to events 
            player.addEventListener('productHover', (e) => console.log('hover:', e.detail.product));
            player.addEventListener('productClick', (e) => console.log('click:', e.detail.product));
            player.addEventListener('productBarMax', () => console.log('bar opened'));
            player.addEventListener('productBarMin', () => console.log('bar closed'));
            player.addEventListener('productHoverPost', (e) => console.log('overlay hover:', e.detail.product));
            player.addEventListener('productClickPost', (e) => console.log('overlay click:', e.detail.product));
            player.addEventListener('replay', () => console.log('replay'));
        });
    </script>
</body>
</html>

PLEASE NOTE

  1. In examples elsewhere you may see markers include seekTime. If present, it controls when a marker appears. If omitted, the marker’s visibility can be inferred from the product’s startTime/endTime. Your implementation can support either pattern, but keep it consistent within your project.

  2. If both markers and onProductClick are used, onProductClick takes precedence.

  3. FastPix Player automatically handles responsiveness.



Troubleshooting

Cart Button Not Displaying

If the cart button isn’t appearing, check these common issues:

  1. Theme not set correctly
<!-- CORRECT --> 
<fastpix-player theme="shoppable-video-player" ...> 
 
<!-- INCORRECT --> 
<fastpix-player theme="default" ...>

  1. Player not initialized

Make sure the player is fully loaded before adding shoppable data:

// Wait for player to be ready 
customElements.whenDefined('fastpix-player').then(() => { 
  const player = document.getElementById('my-player'); 
   
  // Wait for player to be fully initialized 
  player.addEventListener('loadedmetadata', () => { 
    // Now add shoppable data 
    player.addShoppableData(cartData); 
  }); 
});

  1. Missing product data

For shoppable-video-player, you must call addShoppableData():

// REQUIRED for shoppable-video-player 
player.addShoppableData({ 
  productSidebarConfig: { ... }, 
  products: [ ... ] 
})

Note: The product-link attribute is ignored for shoppable-video-player theme. Only shoppable-shorts theme uses the product-link attribute.


  1. CSS Conflicts

Ensure no CSS is hiding the cart button:

/* Check if cart button is hidden */ 
.cartButton { 
  display: none; /* This would hide the button */ 
} 
 
/* Check for other potential conflicts */ 
.cartButton { 
  visibility: hidden; /* This would hide the button */ 
  opacity: 0; /* This would make the button invisible */ 
  z-index: -1; /* This would put the button behind other elements */ 
} 
 
/* Check for responsive hiding */ 
@media (max-width: 150px) { 
  .cartButton { 
    display: none; /* This hides cart button on very small screens */ 
  } 
}

Common CSS issues:

  • CSS Variable syntax: Ensure CSS variables use double dashes (e.g., --shoppable-sidebar-width, not -shoppable-sidebar-width)
  • Theme-specific behavior: shoppable-shorts cart button is always visible regardless of screen size

  1. Force show cart button (Debug)

If the cart button still doesn't appear, you can force it to show:

// Debug method to force show cart button 
const player = document.getElementById('my-player'); 
player.showCartButton(); 
 
// For shoppable-shorts specifically 
if (player.getAttribute('theme') === 'shoppable-shorts') { 
  player.ensureShoppableShortsCartButton(); 
}


Debug steps

  1. Check console: Look for JavaScript errors
  2. Verify theme: Ensure theme="shoppable-video-player" or theme="shoppable-shorts" is set. When using shoppable-video-player, the correct method to pass configuration must be used player.addShoppableData(cartData);
  3. Check network: Ensure player.js is loading correctly (no 404/CORS).
  4. Inspect element: Check if cart button exists in DOM but is hidden