旋转伪元素切割问题

时间:2019-02-27 16:14:56

标签: css pseudo-element

我正在尝试旋转一个具有背景图像的伪元素。 由于背景位于主要元素的中心,因此出于效果目的,旋转时会被切掉。

我创建了一个使用随机图像的示例,目的只是为了说明我的意思。 我想知道这种方法有什么问题,为什么会被淘汰。有什么方法可以旋转背景而不将其剪掉吗?

谢谢。

$(document).ready(function () {
	'use strict';
	$('button').on('click', () => {
		$("li").addClass('issue-simulation');
	})
});
ul {
  display: flex;
  list-style: none;
  padding: 0;
}
ul li {
  position: relative;
  display: flex;
  width: 200px;
  height: 200px;
}
ul li:after {
  content: '';
  position: absolute;
  width: 200px;
  height: 200px;
  background-image: url(https://picsum.photos/180/180);
  background-size: 80%;
  background-repeat: no-repeat;
  background-position: center;
  transition: 650ms cubic-bezier(0.5, 0, 0.1, 1);
}
ul li:hover:after {
  transform: rotate(-10deg);
}
ul li.issue-simulation:after {
  background-position: calc(50% + 50px) center;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<ul>
  <li>
    <img src="https://picsum.photos/200/200" alt="">
  </li>
</ul>
<button>Simulate issue</button>

1 个答案:

答案 0 :(得分:1)

您的问题是因为您正在操纵background-position。您不能强制背景图像溢出其包含的父对象:这是您无法解决的问题。

我相信您的问题可能是XY问题,因为我想您在合成/组合转换时遇到了问题。 类似的事情不会有效

ul li:hover:after {
  transform: rotate(-10deg);
}
ul li.issue-simulation:after {
  transform: translateX(50px);
}

... 因为transform属性不是可加的(即,您不能合并transform属性)

因此,一种正确的解决方案实际上是使用CSS变量:

  1. 声明基本外观

    :root {
      --rotate: 0deg;
      --translateX: 0;
    }
    
  2. 将这些变量应用于伪元素的样式:

    ul li:after {
      transform: translateX(var(--translateX)) rotate(var(--rotate));
    }
    
  3. 然后,您使用JS以编程方式操作这些CSS变量:

    const root = document.documentElement;
    
     $('ul li')
       .on('mouseover', () => root.style.setProperty('--rotate', '-10deg'))
       .on('mouseout', () => root.style.setProperty('--rotate', '0deg'));
    
     $('button').on('click', () => root.style.setProperty('--translateX', '50px'))
    

$(document).ready(function() {
  const root = document.documentElement;

  $('ul li')
    .on('mouseover', () => root.style.setProperty('--rotate', '-10deg'))
    .on('mouseout', () => root.style.setProperty('--rotate', '0deg'));

  $('button').on('click', () => root.style.setProperty('--translateX', '50px'))
});
/* CSS variables */

:root {
  --rotate: 0deg;
  --translateX: 0;
}

ul {
  display: flex;
  list-style: none;
  padding: 0;
}

ul li {
  position: relative;
  display: flex;
  width: 200px;
  height: 200px;
}

ul li::after {
  content: '';
  position: absolute;
  width: 200px;
  height: 200px;
  background-image: url(https://picsum.photos/180/180);
  background-size: 80%;
  background-repeat: no-repeat;
  background-position: center;
  transition: 650ms cubic-bezier(0.5, 0, 0.1, 1);
  /* Apply `transform` to the actual pseudo-element */
  transform: translateX(var(--translateX)) rotate(var(--rotate));
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<ul>
  <li>
    <img src="https://picsum.photos/200/200" alt="">
  </li>
</ul>
<button>Simulate issue</button>