---
title: Widget Embedding
url: https://docs.kaltura.com/docs/conversational-agents/avatar-videos/widget-embedding
---

## Widget Embedding

The VOD Avatar Studio is also available as a drop-in browser widget via the Kaltura embeds framework. The widget uses the server-side API internally and provides a full UI for avatar selection, script editing, AI composition, and video generation.

### Basic Embed

```html
<div id="avatar-studio" style="width: 100%; height: 100vh;"></div>
<script type="module">
  import { loader } from "https://unisphere.nvp1.ovp.kaltura.com/v1/loader/index.esm.js";

  const workspace = await loader({
    serverUrl: "https://unisphere.nvp1.ovp.kaltura.com/v1",
    appId: "my-app",
    appVersion: "1.0.0",
    session: { ks: "$KALTURA_KS", partnerId: $KALTURA_PARTNER_ID },
    runtimes: [{
      widgetName: "unisphere.widget.vod-avatars",
      runtimeName: "studio",
      settings: {
        ks: "$KALTURA_KS",
        partnerId: $KALTURA_PARTNER_ID,
        kalturaServerURI: "https://www.kaltura.com"
      },
      visuals: [{
        type: "page",
        target: "avatar-studio",
        settings: {}
      }]
    }]
  });

  const studio = await workspace.getRuntimeAsync(
    "unisphere.widget.vod-avatars",
    "studio"
  );
</script>
```

### Runtime Settings

| Parameter | Type | Required | Description |
|-----------|------|----------|-------------|
| `ks` | string | yes | Kaltura Session token — user-level (type=0) is sufficient |
| `partnerId` | number | yes | Partner ID — must be a number, not a string |
| `kalturaServerURI` | string | yes | Kaltura API server URL (e.g., `https://www.kaltura.com`) |
| `entryLink` | function | no | `(entryId: string) => string` — returns a URL for navigating to an entry in the host application |
| `handleShare` | function | no | `(entryId: string) => void` — called when the user clicks share on a generated video |
| `allowedProjectTypes` | array | no | Restricts available project types (see below). Default: all types available |
| `initialView` | string | no | `"videoLibrary"` (default) or `"projectBuilder"` — which view to show on load |
| `additionalEsearchFilters` | object | no | Extra eSearch filters for the media picker when selecting source content |
| `loadThumbnailWithKS` | boolean | no | Append KS to thumbnail URLs for access-controlled thumbnails |

### Project Types

The widget supports three project creation flows, controlled by `allowedProjectTypes`:

| Value | Label | Description |
|-------|-------|-------------|
| `"fromScratch"` | Start from scratch | Create an avatar video by writing scenes manually |
| `"session-highlights"` | Create session highlights | AI composes a highlights video from recorded session captions |
| `"video-explainer"` | Generate a video on any topic | AI composes an explainer from video captions and documents |

```javascript
// Only allow manual creation (no AI composition)
settings: {
  ks: "$KALTURA_KS",
  partnerId: $KALTURA_PARTNER_ID,
  kalturaServerURI: "https://www.kaltura.com",
  allowedProjectTypes: ["fromScratch"]
}
```

### Host-Page Callbacks

```javascript
settings: {
  ks: "$KALTURA_KS",
  partnerId: $KALTURA_PARTNER_ID,
  kalturaServerURI: "https://www.kaltura.com",
  entryLink: (entryId) => `https://myapp.com/media/${entryId}`,
  handleShare: (entryId) => {
    navigator.clipboard.writeText(`https://myapp.com/share/${entryId}`);
  }
}
```

### Workspace Lifecycle

```javascript
// Refresh the KS when it approaches expiry
workspace.session.setData(prev => ({ ...prev, ks: "new-ks-value" }));

// Destroy the workspace when the user navigates away
workspace.kill();
```

### Widget Behavior

- **Auto-save:** Scene edits are auto-saved after a 5-second debounce  
- **Polling:** The widget polls `video.get` every 10 seconds during generation  
- **Max scenes:** The widget enforces 20 scenes in its UI  
- **Default avatar:** `jane` template with `#CEEEDB` background
