> ## Documentation Index
> Fetch the complete documentation index at: https://docs.kontext.so/llms.txt
> Use this file to discover all available pages before exploring further.

# TTSDK 播放器

> 通过 KontextVideoTTSDK 产品把 TTSDK 引擎（TTVideoEngine）交给 SDK。

SDK 会跟随你的内容播放器：观众在剧集中的位置，以及内容是否在播放。叠加广告只在内容播放时展示，观众暂停时结束；暂停广告在内容再次播放时结束。使用 TTSDK 播放器（`TTVideoEngine`，BytePlus / 火山引擎点播播放器 SDK）时，一次调用就能把这些都交给 SDK。

## 添加产品

`KontextVideoTTSDK` 是同一个包中的第二个产品。在 Xcode 中，把它与 `KontextVideoSDK` 一起添加（File → Add Package Dependencies，然后勾选两者），或在 `Package.swift` 中：

```swift theme={null}
.target(name: "YourApp", dependencies: [
    .product(name: "KontextVideoSDK", package: "sdk-swift-video"),
    .product(name: "KontextVideoTTSDK", package: "sdk-swift-video"),
]),
```

**不依赖 TTSDK。** TTSDK 以 CocoaPod 形式发布，而 Swift 包无法依赖 CocoaPod。该产品通过引擎的 Objective-C 属性（`currentPlaybackTime`、`playbackState`、`playbackSpeed`）读取它，因此构建时不需要 TTSDK，并使用你应用自己的 TTSDK 和授权。

## 跟随引擎

```swift theme={null}
import KontextVideoTTSDK

ads.track(ttVideoEngine: engine) { episode.id }
```

* 在引擎拿到该集的播放源之后、剧集开始时调用。
* **尾随闭包** 指明引擎正在播放的剧集（它的 vid、它的 URL）。一旦它返回另一个值，该 `VideoAds` 的叠加广告或暂停广告会在 `show` 时抛出 `invalidated(.contentChanged)`。不提供时，只检查引擎是否转到另一个 `VideoAds`。
* **你的 delegate 保持不变。** TTSDK 只有一个 `delegate`，SDK 从不设置它：叠加广告或暂停广告在屏幕上期间，SDK 每秒读取引擎四次，每次 `show` 时也会读取。
* **弱持有：** SDK 绝不会让引擎保持存活。它在 `destroy()` 或下一次 `track` 时放开。

## 在信息流中

短剧信息流通常为每一页提供自己的引擎。为每一页创建自己的 `VideoAds`，并在该页成为当前页时跟随该页的引擎：

```swift theme={null}
func pageDidBecomeCurrent(_ page: EpisodePage) {
    page.ads.track(ttVideoEngine: page.engine) { page.episode.id }
}
```

只在当前页展示叠加广告或暂停广告。广告在屏幕上时被滑走的页面，其广告会在大约一秒内结束（`.interrupted`），以便下一页的广告可以展示。

## SDK 读取什么

| SDK 需要 | 从 TTSDK 读取 |
| - | - |
| 内容的位置 | `currentPlaybackTime`，单位为秒 |
| 是否在播放 | `playbackState` 为播放中。暂停或停止不算播放；缓冲算作播放。 |
| 速度 | `playbackSpeed` |
| 另一集 | 你的闭包返回的值 |
| 拖动进度 | 根据位置推断 |

不是 `TTVideoEngine` 的对象（缺少这些属性）会被当作从不播放来跟随，并在控制台输出错误。


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.