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

# Image to Video API

> Convert static images into dynamic video content with AI-generated motion.

export const ToolSection = ({type = "image", outputs = [], title = "", productSlug = "", apiSlug = ""}) => <>
    <CardGroup cols={2}>
      <Card title={`${title} API reference`} icon="webhook" horizontal href={`/api-reference/${type}-projects/${apiSlug}`}>
        Request fields, responses, and examples
      </Card>
      <Card title="API quickstart" icon="forward-fast" horizontal href="/get-started/quick-start">
        Install an SDK and complete your first generation
      </Card>
    </CardGroup>

    <p>
      Check <a href="/billing/overview">API pricing</a> and <a href="/api-reference/models">model credit costs</a>, then <a href={`https://magichour.ai/developer?tab=api-keys&ref=docs-tool-${apiSlug}&utm_source=docs&utm_medium=referral&utm_campaign=tools`}>create an API key</a>.
    </p>
    <p>
      To try {title} without code, use the <a href={`https://magichour.ai/products/${productSlug}${productSlug.includes("?") ? "&" : "?"}utm_source=docs&utm_medium=referral&utm_campaign=tools`}>browser tool</a>.
    </p>

    {outputs && outputs.length > 0 && <Tabs>
        {outputs.map((output, idx) => <Tab key={idx} title={`Example Output ${idx + 1}`}>
            <Frame>
              {type === "video" ? <video controls preload="metadata" playsInline className="rounded-lg h-80" src={`${output.src}#t=0.001`} type={`${output.src?.endsWith("mp4") ? 'video/mp4' : "video/webm"}`}>
                </video> : type === "audio" ? <audio controls preload="metadata" className="w-full" src={output.src}>
                  Your browser does not support the audio element.
                </audio> : <img height="320" className="rounded-lg h-80" src={output.src} alt={`${title} example output ${idx + 1}`} />}
            </Frame>
          </Tab>)}
      </Tabs>}

  </>;

## Overview

Image to Video converts static images into dynamic video content with AI-generated motion and cinematic effects. The API analyzes images and creates realistic movement, camera motion, and environmental effects to bring still photos to life.

**Processing:** See recent [typical API-job times](/api-reference/processing-times). Jobs run
asynchronously, and duration varies with the input, selected settings, and queue load.

<ToolSection
  title="Image to Video"
  productSlug="image-to-video"
  apiSlug="image-to-video"
  type="video"
  outputs={[
{
  src: "https://d28dkohlqf5vwj.cloudfront.net/products/image-to-video/examples/cinematic-2.mp4",
},
{
  src: "https://d28dkohlqf5vwj.cloudfront.net/products/image-to-video/examples/halo.mp4",
},
]}
/>

## How It Works

1. **Provide a source image** - Upload the image you want to animate
2. Add a prompt to guide movement, or let the model choose.
3. **API generates the video** - AI creates natural motion and effects
4. **Download the result** - Retrieve your animated video

## Use Cases

For a complete product demo workflow, follow the [product video starter recipe](/get-started/starter-recipes). It covers image preparation, video generation, and downloading the result.

* **Social media content** - Turn photos into engaging video posts
* **Marketing videos** - Create dynamic content from product photos
* **Storytelling** - Bring static images to life for narratives
* **Real estate** - Animate property photos for virtual tours
* **E-commerce** - Dynamic product showcases

## Best Practices

### Source Image Quality

<Tip>
  **Use high-quality images with clear subjects** - Better images produce smoother, more realistic
  animations.
</Tip>

* **High resolution** - At least 720p for best results
* **Clear subjects** - Well-defined elements animate better
* **Good composition** - Leave "room" for motion in your frame
* **Appropriate content** - Images with implied motion work well

### Motion Prompts

The motion prompt is optional. Use it to describe the movement you want:

**✅ Good prompts:**

* "Camera slowly panning right, leaves gently swaying in wind"
* "Zoom in on the subject with slight parallax effect"
* "Water rippling, clouds moving slowly across the sky"
* "Person walking forward, hair blowing in breeze"

**❌ Avoid:**

* No motion description: "A beautiful landscape"
* Impossible physics: "Person flying through wall"
* Conflicting motions: "Zoom in and zoom out simultaneously"

### Image Types That Animate Well

| Image Type     | Animation Potential | Tips                                |
| :------------- | :------------------ | :---------------------------------- |
| Landscapes     | Excellent           | Add wind, water, cloud motion       |
| Portraits      | Good                | Subtle movements, blinks, breathing |
| Product photos | Moderate            | Camera motion, lighting effects     |
| Abstract art   | Excellent           | Morphing, flowing effects           |

## Model selection

`model="default"` currently selects `kling-3.0` on paid tiers and `ltx-2.5` on the free tier. Set a model explicitly when your workflow needs a fixed duration and resolution combination. The examples use `ltx-2.5`, which supports five-second clips at 480p; the paid default does not support 480p.

Other current options include `gemini-omni-1.1`, `minimax-h3`, `seedance-2.0-mini`, `seedance-2.5`, and `veo3.1-lite`. Check the [API reference](/api-reference/video-projects/image-to-video) for each model's supported durations, resolutions, and audio settings. Audio is disabled by default and is unavailable on some models.

For a final reference frame, set `assets.end_image_file_path` on a supported model. End-frame support can depend on resolution and duration; for example, Veo 3.1 variants require a duration of eight seconds or less.

## Code Examples

### Basic Image to Video

<CodeGroup>
  ```python Python theme={null}
  from magic_hour import Client
  import os

  client = Client(token=os.getenv("MAGIC_HOUR_API_KEY"))

  result = client.v1.image_to_video.generate(
      assets={
          "image_file_path": "https://raw.githubusercontent.com/runshouse/Sample_Assets/main/sunset.jpg"
      },
      style={
          "prompt":  "Sunset landscape with subtle parallax effect while panning, clouds moving cinematic depth"
      },
      end_seconds=5,
      name="Sunset Animation",
      model="ltx-2.5",
      resolution="480p",
      wait_for_completion=True,
      download_outputs=True,
      download_directory="."
  )

  if result.status == "complete":
      print(f"✅ Video complete!")
      print(f"Downloaded to: {result.downloaded_paths}")
      print(f"Credits charged: {result.credits_charged}")
  else:
      print(f"Job ended with status: {result.status}")
      if result.error:
          print(f"Error: {result.error.message}")
  ```

  ```javascript Node.js theme={null}
  import { Client } from "magic-hour";

  const client = new Client({ token: process.env.MAGIC_HOUR_API_KEY });

  const result = await client.v1.imageToVideo.generate(
    {
      assets: {
        imageFilePath: "https://raw.githubusercontent.com/runshouse/Sample_Assets/main/sunset.jpg",
      },
      style: {
        prompt:
          "Sunset landscape with subtle camera movement, gentle parallax effect, cinematic depth",
      },
      endSeconds: 5,
      name: "Sunset Animation",
      model: "ltx-2.5",
      resolution: "480p",
    },
    {
      waitForCompletion: true,
      downloadOutputs: true,
      downloadDirectory: ".",
    }
  );

  if (result.status === "complete") {
    console.log(`✅ Video complete!`);
    console.log(`Downloaded to: ${result.downloadedPaths}`);
  } else {
    console.error(`Job ended with status: ${result.status}`);
    if (result.error) console.error(result.error.message);
  }
  ```
</CodeGroup>

## Pricing

Image to Video pricing depends on the model, resolution, and duration you choose. You pay for the frames that render. The create response estimates `credits_charged`; read the completed job for the final cost.

## Resolution Limits

Supported resolutions are 360p, 480p, 720p, 1080p, and 4k, depending on the model and your subscription tier. For example, `kling-3.0` supports 4k. Output defaults to `720p` on paid tiers and `480p` on the free tier. See [Resolution Limits](/billing/resolution-limits) for tier details.

<Tip>
  **Try this in our Google Colab Cookbook:** [Run this API with sample
  code](https://colab.research.google.com/drive/1NTHL_lr_s-qBJ-mSecSXPzRLi9_V5JiU?usp=sharing). Just
  add your API key.
</Tip>

## API Reference

<Card title="Image to Video API Reference" icon="webhook" href="/api-reference/video-projects/image-to-video">
  View full API specification
</Card>

## Related Tools

<CardGroup cols={2}>
  <Card title="Product Video Recipe" icon="cart-shopping" href="/get-started/starter-recipes">
    Generate one product clip, compare model costs, and plan a catalog workflow
  </Card>

  <Card title="Text to Video" icon="text" href="/tools/video/text-to-video">
    Generate videos from text descriptions
  </Card>

  <Card title="Animation" icon="film" href="/tools/video/animation">
    Create animated videos with motion effects
  </Card>
</CardGroup>
