Basics of orientation effects
Introduction
amp-orientation-observer combined with amp-animation is a powerful building block that can handle various uses-cases that are dependent on the orientation of the device.
In this tutorial, we will go through some of these use-cases in detail.
Setup
amp-orientation-observer is a functional component that monitors the orientation of the device as it moves, and dispatches alpha
, beta
and gamma
events dependant on what axis the device has moved in. For more details on DeviceOrientationEvents read this article on MDN.
These events in return can be used to seek
animation timelines defined by amp-animation to create orientation based effects.
<script async custom-element="amp-orientation-observer" src="https://cdn.ampproject.org/v0/amp-orientation-observer-0.1.js"></script>
amp-animation is a UI component that relies on Web Animations API to define and run keyframe animations in AMP documents.
<script async custom-element="amp-animation" src="https://cdn.ampproject.org/v0/amp-animation-0.1.js"></script>
Styles
The CSS used for these samples are included here for reference.
These rules are simply needed to make the samples work but are not fundamental to the concepts covered here.
<style amp-custom>
#scrollText {
font-family: Helvetica, sans-serif;
padding: 10px;
max-width: 412px;
height: 500px;
margin: auto;
overflow: hidden;
}
#ipsum {
background-image: linear-gradient(white, deeppink);
}
.clock-hand {
position: absolute;
width: 2vw;
height: 20vw;
max-height: 90px;
max-width: 10px;
top: 50%;
left: 50%;
z-index: 2;
background: #FAFAFA;
transform-origin: 50% 0%;
border-radius: 10px;
transform: rotate(-180deg)
}
.rotate-2 {
transform: rotate(-270deg)
}
</style>
Tilt based scroll animations
Let's create a tilt based scroll animation where you can scroll up and down on a page as you tilt a device along the y axis.
This sample showcases the core concept behind combining amp-orientation-observer
and amp-animation
: The ability to progress through a keyframe animation timeline as the device is tilted.
Our scroll scene is a div
with some Lorem Ipsum text in it. We add an amp-orientation-observer
element as child of the scene to monitor the device's position. Let's take a look at the details:
- on:beta
: This event is triggered by orientation observer as deivce orientation along the beta
axis changes. The event provides a percentage value (decimal between 0 and 1) representing how far the device is within the beta
axis.
- anim.seekTo(percent=event.percent)
: We will define an amp-animation
that will do the spinning in the next step, here we are coupling amp-orientation-observer
and amp-animation
by triggering a seekTo
action on the animation as beta
events occurs. This is how we specify that we like to progress through the animation timeline as the device moves along the beta
axis.
- beta-range
: Each axis has a range of degrees it tracks. For the beta
axis the default range is -180 to 180 degrees. If you want to set the range to something custom as we do in this case you can specify it using the beta-range
attribute here. In this sample we set the beta-range
to "0 180" to make sure that the text doesn't scroll beyond it's first paragraph.
Move phone along y axis to scroll
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Etiam id est et dui maximus sagittis vel imperdiet nibh. Nam finibus nisl sit amet neque gravida pellentesque. Phasellus vulputate, tortor ut pretium ultricies, nibh massa vestibulum nisi, a vestibulum orci velit eget nisl. Maecenas dui nulla, consectetur sed porttitor ac, varius quis nibh. In pellentesque nisi quis ligula fringilla, non lobortis felis tincidunt. Nullam hendrerit sodales purus, nec rhoncus urna ultricies ac. Cras vestibulum pulvinar libero, quis faucibus nisi. Quisque ut lacus vitae justo faucibus mollis vel bibendum neque. Quisque pretium nunc in nunc vulputate, interdum ullamcorper nisl convallis. Cras vitae finibus urna. Sed enim turpis, consectetur eu velit nec, sodales mollis justo. Curabitur pretium luctus felis sagittis rhoncus. Donec vitae vehicula erat, non pellentesque odio. Vestibulum accumsan rhoncus placerat. Donec rutrum ullamcorper sodales. Vestibulum pretium ut diam faucibus tincidunt. Aenean vestibulum nisl nec arcu eleifend posuere. Aliquam nec feugiat nibh. Cras pretium ut purus quis pharetra. Morbi urna augue, lobortis ac porttitor vitae, feugiat eget dui. Nam lacinia commodo tellus vel sagittis. Aliquam id pharetra metus. Nam tristique vulputate maximus. Donec consequat aliquam lacus, ac fermentum magna iaculis tristique. In urna dolor, rutrum non mattis at, luctus nec lectus. Maecenas consequat, massa at placerat convallis, arcu elit consequat nulla, vel egestas justo augue vitae mauris. Nullam est diam, aliquam sit amet posuere non, condimentum et ante. Ut at ullamcorper ipsum. Nullam non efficitur sapien. Praesent vitae odio diam. Nullam dignissim hendrerit neque non tempor. Praesent non arcu volutpat, maximus risus in, rutrum tellus. Quisque nec porttitor purus. Quisque hendrerit erat consequat dignissim vehicula. Quisque tortor orci, bibendum et lacinia at, porttitor nec est. Nunc venenatis sollicitudin dui, et fermentum lectus euismod vitae. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Phasellus diam ante, sagittis non finibus sed, pulvinar id dolor. Maecenas ac facilisis lacus. Suspendisse potenti. Curabitur dignissim consequat ante, quis facilisis ipsum faucibus nec. Suspendisse potenti. Mauris lorem eros, finibus id tincidunt quis, bibendum at urna. Aenean quis tortor ultricies, sodales ipsum id, imperdiet felis. Maecenas vestibulum cursus est convallis imperdiet. In convallis tempus lacus, suscipit tempus turpis mattis id. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Proin massa massa, molestie eu pretium in, eleifend vel erat. Pellentesque dictum turpis sit amet neque elementum aliquam a sed metus. Donec dignissim laoreet massa vel vehicula. Praesent pretium arcu consequat augue dignissim, at ultrices quam placerat. Proin justo odio, fermentum sed malesuada eu, facilisis non quam. In molestie enim nec ligula tempus, sed condimentum dui molestie. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec lobortis, lacus cursus varius malesuada, lacus enim blandit ipsum, non hendrerit est sapien et ex. Nullam quis pulvinar nulla, vitae venenatis massa. In mattis at eros id ullamcorper. Aenean ac hendrerit magna. Sed volutpat sapien quis justo accumsan eleifend. Praesent lobortis, velit sed elementum molestie, urna nibh malesuada lacus, vitae efficitur tellus elit ac augue. Aliquam erat volutpat. Praesent ultricies felis erat, ut luctus nulla pellentesque in. Etiam lacinia neque id neque egestas tempor.End of text
<div id="scrollText">
<amp-orientation-observer beta-range="0 180" on="beta:anim.seekTo(percent=event.percent)" layout="nodisplay">
</amp-orientation-observer>
<div id="ipsum">
<p>Move phone along y axis to scroll</p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Etiam id est et dui maximus sagittis vel imperdiet nibh. Nam finibus nisl sit amet neque gravida pellentesque. Phasellus vulputate, tortor ut pretium ultricies, nibh massa vestibulum nisi, a vestibulum orci velit eget nisl. Maecenas dui nulla, consectetur sed porttitor ac, varius quis nibh. In pellentesque nisi quis ligula fringilla, non lobortis felis tincidunt. Nullam hendrerit sodales purus, nec rhoncus urna ultricies ac. Cras vestibulum pulvinar libero, quis faucibus nisi. Quisque ut lacus vitae justo faucibus mollis vel bibendum neque. Quisque pretium nunc in nunc vulputate, interdum ullamcorper nisl convallis. Cras vitae finibus urna. Sed enim turpis, consectetur eu velit nec, sodales mollis justo. Curabitur pretium luctus felis sagittis rhoncus. Donec vitae vehicula erat, non pellentesque odio. Vestibulum accumsan rhoncus placerat. Donec rutrum ullamcorper sodales. Vestibulum pretium ut diam faucibus tincidunt.
Aenean vestibulum nisl nec arcu eleifend posuere. Aliquam nec feugiat nibh. Cras pretium ut purus quis pharetra. Morbi urna augue, lobortis ac porttitor vitae, feugiat eget dui. Nam lacinia commodo tellus vel sagittis. Aliquam id pharetra metus. Nam tristique vulputate maximus. Donec consequat aliquam lacus, ac fermentum magna iaculis tristique. In urna dolor, rutrum non mattis at, luctus nec lectus. Maecenas consequat, massa at placerat convallis, arcu elit consequat nulla, vel egestas justo augue vitae mauris. Nullam est diam, aliquam sit amet posuere non, condimentum et ante. Ut at ullamcorper ipsum. Nullam non efficitur sapien. Praesent vitae odio diam. Nullam dignissim hendrerit neque non tempor.
Praesent non arcu volutpat, maximus risus in, rutrum tellus. Quisque nec porttitor purus. Quisque hendrerit erat consequat dignissim vehicula. Quisque tortor orci, bibendum et lacinia at, porttitor nec est. Nunc venenatis sollicitudin dui, et fermentum lectus euismod vitae. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Phasellus diam ante, sagittis non finibus sed, pulvinar id dolor. Maecenas ac facilisis lacus. Suspendisse potenti.
Curabitur dignissim consequat ante, quis facilisis ipsum faucibus nec. Suspendisse potenti. Mauris lorem eros, finibus id tincidunt quis, bibendum at urna. Aenean quis tortor ultricies, sodales ipsum id, imperdiet felis. Maecenas vestibulum cursus est convallis imperdiet. In convallis tempus lacus, suscipit tempus turpis mattis id. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Proin massa massa, molestie eu pretium in, eleifend vel erat. Pellentesque dictum turpis sit amet neque elementum aliquam a sed metus. Donec dignissim laoreet massa vel vehicula. Praesent pretium arcu consequat augue dignissim, at ultrices quam placerat. Proin justo odio, fermentum sed malesuada eu, facilisis non quam. In molestie enim nec ligula tempus, sed condimentum dui molestie. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec lobortis, lacus cursus varius malesuada, lacus enim blandit ipsum, non hendrerit est sapien et ex. Nullam quis pulvinar nulla, vitae venenatis massa.
In mattis at eros id ullamcorper. Aenean ac hendrerit magna. Sed volutpat sapien quis justo accumsan eleifend. Praesent lobortis, velit sed elementum molestie, urna nibh malesuada lacus, vitae efficitur tellus elit ac augue. Aliquam erat volutpat. Praesent ultricies felis erat, ut luctus nulla pellentesque in. Etiam lacinia neque id neque egestas tempor.
<h3>End of text</h3>
</div>
</div>
The animation here is a translation along the Y axis to mimic the scrolling action.
<amp-animation id="anim" layout="nodisplay">
<script type="application/json">
{
"duration": "3s",
"fill": "both",
"direction": "alternate",
"animations": [
{
"selector": "#ipsum",
"keyframes": [
{ "transform": "translateY(0)" },
{ "transform": "translateY(-1170px)" }
]
}
]
}
</script>
</amp-animation>
Tilt based translation animations
Let's create a tilt based animation where the clock's hand moves as you tilt the device along a specific axis. The first animation is along the beta
axis, to see this in action rotate your phone along the y axis.
<div id="clock-scene-1" class="clock-scene">
<amp-orientation-observer beta-range="0 180" on="beta:clockAnim1.seekTo(percent=event.percent)" layout="nodisplay">
</amp-orientation-observer>
<amp-img layout="responsive" width="2" height="1.5" src="/static/samples/img/clock.jpg">
<div class="clock-hand rotate-1"></div>
</amp-img>
</div>
The animation in this case is a rotation of the clock hand from -180 degrees to 180 degrees to allow the hand to start and end at the 12 o' clock position.
<amp-animation id="clockAnim1" layout="nodisplay">
<script type="application/json">
{
"duration": "3s",
"fill": "both",
"direction": "alternate",
"animations": [
{
"selector": "#clock-scene-1 .rotate-1",
"keyframes": [
{ "transform": "rotate(-180deg)" },
{ "transform": "rotate(180deg)" }
]
}
]
}
</script>
</amp-animation>
The second animation is along the gamma
axis, to see this in action rotate your phone along the x axis:
<div id="clock-scene-2" class="clock-scene">
<amp-orientation-observer on="gamma:clockAnim2.seekTo(percent=event.percent)" layout="nodisplay">
</amp-orientation-observer>
<amp-img layout="responsive" width="2" height="1.5" src="/static/samples/img/clock.jpg">
<div class="clock-hand rotate-2"></div>
</amp-img>
</div>
The animation in this case is a rotation of the clock hand from -270 degrees to 90 degrees to allow the hand to start and end at the 12 o' clock position. The motion here is limited from the 9 o' clock position to the 3 o' clock position.
<amp-animation id="clockAnim2" layout="nodisplay">
<script type="application/json">
{
"duration": "3s",
"fill": "both",
"direction": "alternate",
"animations": [
{
"selector": "#clock-scene-2 .rotate-2",
"keyframes": [
{ "transform": "rotate(-270deg)" },
{ "transform": "rotate(-90deg)" }
]
}
]
}
</script>
</amp-animation>
The third animation is along the alpha
axis, to see this in action rotate your phone along the horizontal axis:
<div id="clock-scene-3" class="clock-scene">
<amp-orientation-observer alpha-range="0 360" on="alpha:clockAnim3.seekTo(percent=event.percent)" layout="nodisplay">
</amp-orientation-observer>
<amp-img layout="responsive" width="2" height="1.5" src="/static/samples/img/clock.jpg">
<div class="clock-hand rotate-3"></div>
</amp-img>
</div>
The animation in this case is a rotation of the clock hand from 90 degrees to -270 degrees to allow the hand to start and end at the 12 o' clock position.
<amp-animation id="clockAnim3" layout="nodisplay">
<script type="application/json">
{
"duration": "3s",
"fill": "both",
"direction": "alternate",
"animations": [
{
"selector": "#clock-scene-3 .rotate-3",
"keyframes": [
{ "transform": "rotate(90deg)" },
{ "transform": "rotate(-270deg)" }
]
}
]
}
</script>
</amp-animation>
이 페이지의 설명만으로 궁금한 점이 모두 해결되지 않는다면 다른 AMP 사용자에게 문의하여 구체적인 활용 사례를 논의해 보세요.
Stack Overflow로 이동 설명이 부족한 기능을 발견하셨나요?AMP 프로젝트는 여러분의 참여와 기여를 적극 환영합니다! 오픈 소스 커뮤니티를 통해 지속적으로 활동해 주셔도 좋지만 관심 있는 주제에 한 번만 기여하셔도 큰 도움이 됩니다.
GitHub에서 샘플 수정하기-
Written by @nainar