如何在网站中进行共享元素转换
How to make a shared element transition in website
我想在网站中进行共享元素转换(Android),如下图所示:
点击图片后,图片会从原来的位置平滑移动到屏幕中心,背景会变成白色。我该怎么做?
谢谢。
$('.media>img').click(function(){
$(this).toggleClass('open');
})
body {
background-color:#fff;
color: var(--color-gray-2);
font: var(--font-body);
margin: 0;
padding:0;
}
.post {
margin-bottom: var(--unit-xxl);
}
.post + .post:before {
content: "- { · · · } -";
display: block;
font: var(--font-text);
margin: 0 auto;
text-align: center;
width: 50vw;
}
.post > * {
width: 60vw;
max-width: 892px;
margin-left: auto;
margin-right: auto;
}
.post > * + * {
margin-top: var(--unit-m);
}
.hero {
margin-bottom: var(--unit-xl);
}
h1 {
color: var(--color-white);
font: var(--font-title-1);
margin-bottom: 0.2em;
margin-top: var(--unit-xxl);
}
h2 {
color: var(--color-white);
font: var(--font-title-2);
margin-bottom: 0.5em;
}
h3 {
font: var(--font-title-3);
margin-bottom: 0.5em;
}
.post * + h2,
.post * + h3 {
margin-top: var(--unit-xl); /* if it's not the first element */
}
.post h1 + h2,
.post h1 + h3,
.post h2 + h3 {
margin-top: 0; /* if it's like a tagline */
}
.post h1 + h3 + * {
margin-top: var(--unit-xl); /* this indicates the header */
}
p {
font: var(--font-text);
}
ul {
font: var(--font-text);
list-style: inside;
}
a {
color: var(--color-gray-4);
font-weight: 500;
text-decoration: none;
}
a:hover {
color: var(--color-white);
}
.post figcaption {
text-align: center;
margin-top: var(--unit-xxs);
}
.post img {
display: block;
width: 100%;
transition:all 0.3s ease;
}
.media {
margin-top: var(--unit-xl);
margin-bottom: var(--unit-xl);
}
img.open{
transform:scale(1.4);
box-shadow:0 0 0 2000px rgba(255,255,255,0.8);
}
.media > * {
margin-left: auto;
margin-right: auto;
text-align: center;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.1/jquery.min.js"></script>
<article class="post">
<p>The date is October 1st, 2015. For the last 3 hours, I've been researching as much as I can about Mars occasionally stopping to drool over those beautiful red-tinted landscapes. I'm working on an email campaign titled Add Mars to your travel bucket-list - funny for a designer at <a href="booking.com">Booking.com</a>, <em>"Planet Earth's #1 Accommodation Site"</em>.</p>
<div class="media">
<img src="https://cdn-images-1.medium.com/max/800/1*BEEp4hungBtNQslF-UwKzw.png" />
</div>
</div>
<p>These places are scattered all over the globe, some only 3 hours away from our office here in Amsterdam.</p>
<p>Once the list was complete, we took the idea to our copywriters and they eagerly jumped on board. After that, all we needed was a back-end developer and 14 hours later we'd created an email and <a href="https://dribbble.com/shots/2299776-Get-ready-for-the-Final-Frontier">this landing page</a> from scratch.</p>
</article>
这是使用香草 javascript 的解决方案。它也适用于响应式网站。
const imgs = document.getElementsByClassName("img"),
blurry = document.getElementById("blurry");
let isOpened = false, // if some image is opened
openedImageIndex = -1; // image index in imgs array, which is currently opened
const closeModal = () => {
isOpened = false;
imgs[openedImageIndex].style.transform = "translate(0,0)"; // move image back to original position
blurry.classList.toggle("display");
setTimeout(() => (imgs[openedImageIndex].style.zIndex = "3"), 600);
};
//Close modal on scrolling event
window.addEventListener("scroll", () => {
if (isOpened) {
closeModal();
}
});
//Close modal when click on outside image
blurry.addEventListener("click", () => {
closeModal();
});
//If your page has more than one image
for (let i = 0; i < imgs.length; ++i) {
imgs[i].addEventListener("click", function () {
if (isOpened) {
isOpened = false;
this.style.transform = "translate(0,0)";
blurry.classList.toggle("display");
setTimeout(() => (this.style.zIndex = "3"), 600); //time should be greater than animation time duration in css
} else {
isOpened = true;
openedImageIndex = i;
const screenWidth = document.documentElement.clientWidth,
screenHeight = document.documentElement.clientHeight,
imgPos = this.getBoundingClientRect(),
imgWidth = this.clientWidth,
imgHeight = this.clientHeight;
const imgTop = imgPos.top,
imgLeft = imgPos.left;
const req_top = (screenHeight - imgHeight) / 2 - imgTop, //required top, left value to make sure the image moves to center on screen
req_left = (screenWidth - imgWidth) / 2 - imgLeft;
this.style.transform = "translate(" + req_left + "px," + req_top + "px)";
this.style.zIndex = "5";
blurry.classList.toggle("display");
}
});
}
body {
background-color: black;
}
p {
color: white;
}
.shared-element-transition {
width: 79vw;
margin: 0 auto;
}
.shared-element-transition p {
line-height: 1.5em;
}
.shared-element-transition img {
cursor: -webkit-zoom-in;
cursor: zoom-in;
z-index: 3;
position: relative;
display: block;
margin: 30px auto;
max-width: 80%;
-webkit-transition: -webkit-transform 0.5s ease;
transition: -webkit-transform 0.5s ease;
transition: transform 0.5s ease;
transition: transform 0.5s ease, -webkit-transform 0.5s ease;
}
.shared-element-transition #blurry {
cursor: -webkit-zoom-out;
cursor: zoom-out;
top: 0;
left: 0;
z-index: 4;
width: 100%;
height: 100vh;
position: fixed;
background-color: #333333;
-webkit-transition: opacity 0.5s ease, visibility 0.5s ease;
transition: opacity 0.5s ease, visibility 0.5s ease;
opacity: 0;
visibility: hidden;
}
.shared-element-transition #blurry.display {
visibility: visible;
opacity: 1;
}
<div class="shared-element-transition">
<div id="blurry"></div>
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
<img class="img" src="https://picsum.photos/600/400">
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
<img class="img" src="https://picsum.photos/400/300" alt="">
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
</div>
我想在网站中进行共享元素转换(Android),如下图所示:
点击图片后,图片会从原来的位置平滑移动到屏幕中心,背景会变成白色。我该怎么做?
谢谢。
$('.media>img').click(function(){
$(this).toggleClass('open');
})
body {
background-color:#fff;
color: var(--color-gray-2);
font: var(--font-body);
margin: 0;
padding:0;
}
.post {
margin-bottom: var(--unit-xxl);
}
.post + .post:before {
content: "- { · · · } -";
display: block;
font: var(--font-text);
margin: 0 auto;
text-align: center;
width: 50vw;
}
.post > * {
width: 60vw;
max-width: 892px;
margin-left: auto;
margin-right: auto;
}
.post > * + * {
margin-top: var(--unit-m);
}
.hero {
margin-bottom: var(--unit-xl);
}
h1 {
color: var(--color-white);
font: var(--font-title-1);
margin-bottom: 0.2em;
margin-top: var(--unit-xxl);
}
h2 {
color: var(--color-white);
font: var(--font-title-2);
margin-bottom: 0.5em;
}
h3 {
font: var(--font-title-3);
margin-bottom: 0.5em;
}
.post * + h2,
.post * + h3 {
margin-top: var(--unit-xl); /* if it's not the first element */
}
.post h1 + h2,
.post h1 + h3,
.post h2 + h3 {
margin-top: 0; /* if it's like a tagline */
}
.post h1 + h3 + * {
margin-top: var(--unit-xl); /* this indicates the header */
}
p {
font: var(--font-text);
}
ul {
font: var(--font-text);
list-style: inside;
}
a {
color: var(--color-gray-4);
font-weight: 500;
text-decoration: none;
}
a:hover {
color: var(--color-white);
}
.post figcaption {
text-align: center;
margin-top: var(--unit-xxs);
}
.post img {
display: block;
width: 100%;
transition:all 0.3s ease;
}
.media {
margin-top: var(--unit-xl);
margin-bottom: var(--unit-xl);
}
img.open{
transform:scale(1.4);
box-shadow:0 0 0 2000px rgba(255,255,255,0.8);
}
.media > * {
margin-left: auto;
margin-right: auto;
text-align: center;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.1/jquery.min.js"></script>
<article class="post">
<p>The date is October 1st, 2015. For the last 3 hours, I've been researching as much as I can about Mars occasionally stopping to drool over those beautiful red-tinted landscapes. I'm working on an email campaign titled Add Mars to your travel bucket-list - funny for a designer at <a href="booking.com">Booking.com</a>, <em>"Planet Earth's #1 Accommodation Site"</em>.</p>
<div class="media">
<img src="https://cdn-images-1.medium.com/max/800/1*BEEp4hungBtNQslF-UwKzw.png" />
</div>
</div>
<p>These places are scattered all over the globe, some only 3 hours away from our office here in Amsterdam.</p>
<p>Once the list was complete, we took the idea to our copywriters and they eagerly jumped on board. After that, all we needed was a back-end developer and 14 hours later we'd created an email and <a href="https://dribbble.com/shots/2299776-Get-ready-for-the-Final-Frontier">this landing page</a> from scratch.</p>
</article>
这是使用香草 javascript 的解决方案。它也适用于响应式网站。
const imgs = document.getElementsByClassName("img"),
blurry = document.getElementById("blurry");
let isOpened = false, // if some image is opened
openedImageIndex = -1; // image index in imgs array, which is currently opened
const closeModal = () => {
isOpened = false;
imgs[openedImageIndex].style.transform = "translate(0,0)"; // move image back to original position
blurry.classList.toggle("display");
setTimeout(() => (imgs[openedImageIndex].style.zIndex = "3"), 600);
};
//Close modal on scrolling event
window.addEventListener("scroll", () => {
if (isOpened) {
closeModal();
}
});
//Close modal when click on outside image
blurry.addEventListener("click", () => {
closeModal();
});
//If your page has more than one image
for (let i = 0; i < imgs.length; ++i) {
imgs[i].addEventListener("click", function () {
if (isOpened) {
isOpened = false;
this.style.transform = "translate(0,0)";
blurry.classList.toggle("display");
setTimeout(() => (this.style.zIndex = "3"), 600); //time should be greater than animation time duration in css
} else {
isOpened = true;
openedImageIndex = i;
const screenWidth = document.documentElement.clientWidth,
screenHeight = document.documentElement.clientHeight,
imgPos = this.getBoundingClientRect(),
imgWidth = this.clientWidth,
imgHeight = this.clientHeight;
const imgTop = imgPos.top,
imgLeft = imgPos.left;
const req_top = (screenHeight - imgHeight) / 2 - imgTop, //required top, left value to make sure the image moves to center on screen
req_left = (screenWidth - imgWidth) / 2 - imgLeft;
this.style.transform = "translate(" + req_left + "px," + req_top + "px)";
this.style.zIndex = "5";
blurry.classList.toggle("display");
}
});
}
body {
background-color: black;
}
p {
color: white;
}
.shared-element-transition {
width: 79vw;
margin: 0 auto;
}
.shared-element-transition p {
line-height: 1.5em;
}
.shared-element-transition img {
cursor: -webkit-zoom-in;
cursor: zoom-in;
z-index: 3;
position: relative;
display: block;
margin: 30px auto;
max-width: 80%;
-webkit-transition: -webkit-transform 0.5s ease;
transition: -webkit-transform 0.5s ease;
transition: transform 0.5s ease;
transition: transform 0.5s ease, -webkit-transform 0.5s ease;
}
.shared-element-transition #blurry {
cursor: -webkit-zoom-out;
cursor: zoom-out;
top: 0;
left: 0;
z-index: 4;
width: 100%;
height: 100vh;
position: fixed;
background-color: #333333;
-webkit-transition: opacity 0.5s ease, visibility 0.5s ease;
transition: opacity 0.5s ease, visibility 0.5s ease;
opacity: 0;
visibility: hidden;
}
.shared-element-transition #blurry.display {
visibility: visible;
opacity: 1;
}
<div class="shared-element-transition">
<div id="blurry"></div>
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
<img class="img" src="https://picsum.photos/600/400">
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
<img class="img" src="https://picsum.photos/400/300" alt="">
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
<p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the
industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into
electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like
Aldus PageMaker including versions of Lorem Ipsum.</p>
</div>