#BlackLivesMatter
AMP
  • stories

Ken Burns

Introduction

Best known for his work on documentaries, Ken Burns developed a signature effect which consisted of a combination of panning and zooming over an image. It has since been used popularly. We can achieve this simple yet captivating effect by combining the 'pan' and 'zoom' animations in amp-story. Here's how to do it.

Ken Burns Effect

The general idea is to nest elements to combine the animations: the container element will animate the zoom, and the image inside the container will be animated with a panning.

  • Start by creating an <amp-story-page> with a <amp-story-grid-layer using the fill template.
  • Add a <div> element which will act as the image container. Set its style class to position:absolute. This will ensure image coordinates correspond to those of the viewport, which is important for the animation.
  • Set its animation to be animate-in="zoom-in" or animate-in="zoom-out" and its duration with "animate-in-duration=30s".

In this demo we use 30 seconds but your mileage may vary. Try experimenting with different values to see what works best for your desired results.

  • Inside this container, add an <amp-img> element with the src attribute pointing at your image, describe the size of the image with the width and height attributes of the <amp-img> element. Set layout="fixed" so that the image outsizes the screen real estate (We want to use a large image that can be panned over. We recommend 1600 x 1200 px or larger).
  • Animate the <amg-img> element using the animate-in="pan-right". (You can also use pan-left, pan-up, and pan-down). See amp-story animations list.

It's important that the image sets the panning animation, whereas the image container sets the zoom animation. Otherwise the dimensions of the image will change, causing undesired results in the animation.

<amp-story-page id="ken-burns-effect1">
  <amp-story-grid-layer template="fill">
    <div animate-in="zoom-in"
      animate-in-duration="30s"
      class="img-container">
      <amp-img id="ken-burns-img1"
        src="https://picsum.photos/1600/1200?image=1077"
        animate-in="pan-left"
        animate-in-duration="30s"
        layout="fixed"
        width="1600"
        height="1200">
      </amp-img>
    </div>
  </amp-story-grid-layer>
</amp-story-page>

Using Multiple Images

You can even implement a slideshow transitioning between multiple pages using this effect.

Just combine the animations as described in the combining animations section. Remember all the elements being animated after certain animation must include the animate-in-after attribute. Including the children being animated. See below for the code sample.

We also reset the sizes of the nested <div> elements so that they don't change the dimensions used for the animations. See the img-container style class in the code sample.

Keep in mind results may vary depending on the image size and animations you use. Experiment with different animation durations and presets to see what you like best!

<amp-story-page id="ken-burns-effect2">
  <amp-story-grid-layer template="fill">
    <div animate-in="zoom-in"
      animate-in-duration="5s"
      class="img-container">
      <amp-img id="ken-burns-img2"
        src="https://picsum.photos/1600/1200?image=1078"
        animate-in="pan-right"
        animate-in-duration="5s"
        layout="fixed"
        width="1600"
        height="1200">
      </amp-img>
    </div>
    <div animate-in="fade-in"
      animate-in-after="ken-burns-img2"
      animate-in-duration="1s"
      class="img-container">
      <div animate-in="zoom-out"
        animate-in-duration="5s"
        class="img-container"
        animate-in-after="ken-burns-img2">
        <amp-img id="ken-burns-img3"
          src="https://picsum.photos/1600/1200?image=1026"
          layout="fixed"
          width="1600"
          height="1200"
          animate-in="pan-down"
          animate-in-duration="5s"
          animate-in-after="ken-burns-img2">
        </amp-img>
      </div>
    </div>
    <div animate-in="fade-in"
      animate-in-after="ken-burns-img3"
      animate-in-duration="1s"
      class="img-container">
      <div animate-in="zoom-in"
        animate-in-duration="5s"
        class="img-container"
        animate-in-after="ken-burns-img3">
        <amp-img id="ken-burns-img4"
          src="https://picsum.photos/1600/1200?image=1029"
          layout="fixed"
          width="1600"
          height="1200"
          animate-in="pan-right"
          animate-in-duration="5s"
          animate-in-after="ken-burns-img3">
        </amp-img>
      </div>
    </div>
    <div animate-in="fade-in"
      animate-in-after="ken-burns-img4"
      animate-in-duration="1s"
      class="img-container">
      <div animate-in="zoom-out"
        animate-in-duration="5s"
        class="img-container"
        animate-in-after="ken-burns-img4">
        <amp-img id="ken-burns-img5"
          src="https://picsum.photos/1600/1200?image=1033"
          layout="fixed"
          width="1600"
          height="1200"
          animate-in="pan-up"
          animate-in-duration="5s"
          animate-in-after="ken-burns-img4">
        </amp-img>
      </div>
    </div>
  </amp-story-grid-layer>
</amp-story-page>

If you want a slower movement for each image and don't want to wait for the first image to be done animating to start animating the second one, you can use the animate-in-delay attribute on the second image. Set it to the amount of seconds that you want the first image to display before the second image appears.

<amp-story-page id="ken-burns-effect3">
  <amp-story-grid-layer template="fill">
    <div>
      <div animate-in="zoom-in"
        animate-in-duration="30s"
        class="img-container">
        <amp-img src="https://picsum.photos/1600/1200?image=1078"
          animate-in="pan-right"
          animate-in-duration="30s"
          layout="fixed"
          width="1600"
          height="1200">
        </amp-img>
      </div>
      <div animate-in="fade-in"
        animate-in-delay="5s"
        animate-in-duration="1s"
        class="img-container">
        <div animate-in="zoom-out"
          animate-in-duration="30s"
          class="img-container"
          animate-in-delay="5s">
          <amp-img src="https://picsum.photos/1600/1200?image=1026"
            layout="fixed"
            width="1600"
            height="1200"
            animate-in="pan-up"
            animate-in-duration="30s"
            animate-in-delay="5s">
          </amp-img>
        </div>
      </div>
      <div animate-in="fade-in"
        animate-in-delay="10s"
        animate-in-duration="1s"
        class="img-container">
        <div animate-in="zoom-out"
          animate-in-duration="30s"
          class="img-container"
          animate-in-delay="10s">
          <amp-img src="https://picsum.photos/1600/1200?image=1029"
            layout="fixed"
            width="1600"
            height="1200"
            animate-in="pan-right"
            animate-in-duration="30s"
            animate-in-delay="10s">
          </amp-img>
        </div>
      </div>
      <div animate-in="fade-in"
        animate-in-delay="15s"
        animate-in-duration="1s"
        class="img-container">
        <div animate-in="zoom-out"
          animate-in-duration="30s"
          class="img-container"
          animate-in-delay="15s">
          <amp-img src="https://picsum.photos/1600/1200?image=1033"
            layout="fixed"
            width="1600"
            height="1200"
            animate-in="pan-left"
            animate-in-duration="30s"
            animate-in-delay="15s">
          </amp-img>
        </div>
      </div>
    </div>
  </amp-story-grid-layer>
</amp-story-page>
자세한 설명이 필요하신가요?

이 페이지의 설명만으로 궁금한 점이 모두 해결되지 않는다면 다른 AMP 사용자에게 문의하여 구체적인 활용 사례를 논의해 보세요.

Stack Overflow로 이동
설명이 부족한 기능을 발견하셨나요?

AMP 프로젝트는 여러분의 참여와 기여를 적극 환영합니다! 오픈 소스 커뮤니티를 통해 지속적으로 활동해 주셔도 좋지만 관심 있는 주제에 한 번만 기여하셔도 큰 도움이 됩니다.

GitHub에서 샘플 수정하기