re-rotated 元素中的属性背后的计算是什么?

What are the calculations behind the properties in a re-rotated element?

我一直在研究接触式卡片之类的东西。 Apparently 六边形是一个相当新的趋势,但我想让它更简单一点,即:旋转正方形。考虑到我对 HTML 和 CSS 非常了解,实现这个并不难。几分钟后我想出了 this.

HTML

<a href="#" title="Profile of Banana">
    <span style="background-image: url(http://s5.favim.com/orig/52/portrait-sigma-50mm-f1.4-hsm-canon-eos-5d-mk2-face-Favim.com-473053.jpg);">
        Queen Elizabeth
    </span>
</a>

CSS

a {
    display: inline-block;
    margin: 50px;
    width: 150px;
    height: 150px;
    transform: rotate(45deg);
    position: relative;
    overflow: hidden;
}

/* Pseudo element for border */
a:after {
    content: "";
    display: block;
    width: 142px;
    width: calc(100% - 8px);
    height: 142px;
    height: calc(100% - 8px);
    border: 2px solid white;
    position: relative;
    z-index: 10;
    top: 4px;
    left: 4px;
}

/* Span for bg-image and text */
a > span {
    display: block;
    height: 213px;
    width: 213px;
    top: -31px;
    left: -31px;
    position: absolute;
    background-size: cover;
    background-position: center;
    transform: rotate(-45deg);
    padding: 76px 24px 0;
}

这个想法很简单:

这适用于所有主流浏览器,并在其他浏览器(IE8 及更低版本;尽管您可能需要 background size polyfill)中优雅地降级为简单的正方形。出于这个原因,我想保留这个 HTML 结构。

所以,问题是什么?首先,我想让它适用于不同的尺寸,我只需要设置 link 本身 (a) 的宽度和高度,然后设置其 [= 的高度和宽度74=] 是自动计算的——在我的项目中,我可以使用相对较新的 CSS3 calc() 函数,如果这有任何帮助的话,还有 SASS/SCSS 的美感。换句话说,我需要 a 的宽度与其 child span 之间的比率。据我所知,该比率似乎是 2 的平方根:213 / 150 = 1.42。那么,我的第一个问题是,为什么?这背后的逻辑and/or算术是什么?为什么跨度不能简单地占据其 parent 的 100% 宽度?为什么需要它正好是平方根的 2 倍?

另外,我也想知道top和left的值是从哪里来的。我还没有弄清楚哪种算术可能是 is 的基础。我知道这可能取决于 transform-origin 的值,但我不知道具体如何。换句话说,pre-defined transform-origin 值是否有可能使 topleft 为零,这样就不需要 per-case计算值?如果不是,如何根据其 parent 的宽度值计算这些属性的值,因为这是唯一应该知道的值?

总结一下,如果只知道a的宽高,我怎么办:

我不想为此使用任何 JS 解决方案。如果有什么不清楚的地方,请 post 发表评论,以便我澄清。

UPDATED FIDDLE

首先,由于为 span 定义的背景图像将与实际的 a 元素重叠,因此它需要更大一些。当我们谈论 45 度角时,这会导致三角形截断形状,其中主正方形(即图像)的大小是长边,另外两条大小相同的线是锚点.因此,图像的大小(span)应该等于sqrt(2)*100% ~= 141.42%.

然后span的定位。首先我们将图像旋转 45 度。此操作的重要意义在于 transform-origin 设置为 0 0 而不是 50% 50%。通过这样做,元素将围绕菱形顶部中间的单个点旋转。旋转后,只需在 X 轴上平移元素即可,这也可以通过 CSS 变换完成:translateX(-50%).

无论现在传递给 a 的宽度和高度的值是什么,图像都应该始终在其中完美对齐,尺寸正确。

(在 fiddle 中,尝试给 a 一个值,比如 400px。它看起来不错,不是吗?你也可以给图像 nice hover effects .)

a {
    display: inline-block;
    width: 200px;
    height: 200px;
    transform: rotate(45deg)  translate(50%);
    position: relative;
    overflow: hidden;
}
a:after {
    content: "";
    display: block;
    width: calc(100% - 8px);
    height: calc(100% - 8px);
    border: 2px solid white;
    position: relative;
    z-index: 10;
    top: 4px;
    left: 4px;
}
a > span {
    display: block;
    height: 141.42%;
    width: 141.42%;
    top: 0;
    left: 0;
    position: absolute;
    background-size: cover;
    background-position: center;
    transform: rotate(-45deg) translateX(-50%);
    transform-origin: 0 0;
}