Get set up

Hot Takes lets your stakeholders give feedback from right inside your prototype: the same in-context markup and comments you used to get from your design tool of choice, now on a real iOS build. They annotate screenshots and record their screen as they go, and every take lands in a shared gallery tied to a verified person. Here's how to add it to your app.

Requirements

  • iOS 17 or later.
  • Swift Package Manager (the SDK ships as a SwiftPM package).
  • Zero third-party dependencies: the package pulls in nothing else.

1. Create a project

In your dashboard, create a project and copy its project key: a string that looks like ht_pk_…. Each project has its own key; captures made with that key show up in that project's gallery.

2. Add the package

The SDK ships as a Swift package, so it goes in through Xcode's built-in package manager. No CocoaPods, no scripts.

  1. Open your project in Xcode: the .xcodeproj or .xcworkspace you build your prototype from.
  2. From the menu bar, choose File → Add Package Dependencies… The package dialog opens.
  3. Paste the package URL into the search field in the top-right corner of the dialog: https://github.com/gouliard/hottakes-ios.git
  4. Select the hottakes-ios package when it appears in the list.
  5. Leave the Dependency Rule set to “Up to Next Major Version”, the default. You'll get compatible updates automatically, and nothing that could break your build.
  6. Under Add to Project, make sure your project is selected, then click Add Package. Xcode fetches the package and resolves it.
  7. A “Choose Package Products” sheet appears. Check that the HotTakes library's “Add to Target” column shows your app target (not a test or extension target), then click Add Package again.

That's it. To confirm it worked: the package appears under Package Dependencies at the bottom of Xcode's Project navigator, and your target's General tab lists HotTakes under “Frameworks, Libraries, and Embedded Content”. If import HotTakes compiles, you're ready for step 3.

Already have the project editor open? The same flow starts from the project's Package Dependencies tab: select your project (not a target) in the navigator, open the tab, and click the + button at the bottom of the list. Both paths open the same dialog.

3. Start the SDK

The integration is an import and a single call. Both have a specific home:

  1. Open your app's entry point: the file with the @main attribute on your App struct (often named after your app, like MyPrototypeApp.swift).
  2. Add import HotTakes at the top of the file, alongside import SwiftUI. Imports only compile at file scope: if you paste it inside the struct, Xcode reports “Declaration is only valid at file scope”.
  3. Call HotTakes.start(...) inside the struct's init(). If your App struct doesn't have an init yet, add one; if it already has one, put the call at the end of it. (The call goes inside init's braces: at file level, Xcode reports “Expressions are not allowed at the top level”.)

The whole file, for a prototype that had no init before:

import SwiftUI
import HotTakes

@main
struct MyPrototypeApp: App {
    init() {
        HotTakes.start(
            projectKey: "ht_pk_your_key_here",
            apiBaseURL: URL(string: "https://api.hottakes.app/api/sdk/v1")!
        )
    }

    var body: some Scene {
        WindowGroup { ContentView() }
    }
}

Swap in your own project key from step 1, build and run, and the floating capture pill appears in your running app. Your reviewers do everything else from there.

Call start() unconditionally: do not wrap it in #if DEBUG. TestFlight builds are Release builds, so an #if DEBUG guard compiles the call out of the exact builds your reviewers use. The SDK manages this for you: it is active in TestFlight and development builds and stays dormant in a real App Store build, so the unconditional call is always safe to ship. (If you deliberately want capture live in a production App Store release too, pass activateInAppStore: true; TestFlight and development builds are always active regardless.)

Trigger options

By default the SDK shows a draggable pill your reviewers tap to capture. For a hands-off demo-day build you can switch to a shake gesture instead (trigger: .shake), so there's no visible UI until someone shakes the device. The web app's New Project dialog also asks which trigger you plan to use, but that's only a label for your own reference on the dashboard card: it doesn't configure your build remotely, so make sure the code you ship matches what you picked there.

Accent color

The SDK's surfaces (sheet primary buttons, the viewport glow while capturing) pick up your project's accent color automatically once a reviewer is enrolled. Before that, the optional accentColor: parameter to start() sets the fallback (default red). The capture pill itself is monochrome and is never tinted by either value.

Required Info.plist keys

A screen recording captures live microphone audio mixed into its video (there's no separate voice-clip capture on a screenshot), so your host app must declare a matching usage description in its Info.plist:

  • A microphone usage description (NSMicrophoneUsageDescription), shown when a reviewer starts narrating a screen recording.

Screen recording itself needs no Info.plist entry: ReplayKit shows its own system consent UI when a reviewer starts recording. If the microphone description is missing, the SDK fails loudly in a debug build (so you catch it during development) and degrades gracefully in a release build (recording capture is disabled rather than crashing; screenshots are unaffected).

What data the SDK collects

Every capture carries basic device/app context (device model, OS version, your app's version and build, and screen dimensions), attached automatically so your team can reproduce what the reviewer saw. Screenshots include the reviewer's annotations and any typed note; recordings include the screen video plus live microphone audio, mixed in as narration. The Privacy Policy covers the full list of what's collected and how it's stored.

Testing your integration

Screenshots work everywhere, including the iOS Simulator. Screen recording requires a real device (iPhone or iPad): ReplayKit isn't available in the Simulator. The example host app in the SDK repo is a working reference integration to compare against.

Regenerating your project key

You can regenerate a project key from the project page's “Hot Takes Project Key” button. This only affects new enrollments going forward: reviewers who already enrolled keep working, and existing captures are untouched. Regenerate if a key leaks or you want to cut off future enrollment against an old build.

Troubleshooting

  • Pill not appearing: confirm HotTakes.start(projectKey:apiBaseURL:) runs at launch and the key is a valid ht_pk_… string for a live project.
  • Uploads stuck / spooling: captures are spooled and retried when the device is offline: they'll upload once connectivity returns; nothing is lost.
  • “Invalid key” state: the key doesn't match a project (typo, or the key was regenerated); copy it again from the project page's “Hot Takes Project Key” button.
  • Recording disabled: you're on the Simulator, or the microphone Info.plist usage description is missing (see above).

Need a hand?

Use the support form.