热门标签 | HotTags
当前位置:  开发笔记 > 后端 > 正文

CSS3的2D与3D转换

2D和3D转换涉及到数学中的知识,作为一个数学专业的毕业生,不研究一下岂不是对不起自己的专业?首先来看几个参数:1、transform-origin:origin(起源,起点),也即变形的起点,在

2D和3D转换涉及到数学中的知识,作为一个数学专业的毕业生,不研究一下岂不是对不起自己的专业?

首先来看几个参数:

1、transform-origin:origin(起源,起点),也即变形的起点,在数学上可以理解为坐标原点。

  其语法为:transform-origin:[ | | left | center | right | top | bottom] | [ | | left | center | right] | [[ | | left | center | right] && [ | | top | center | bottom]] ?

  描述为普通语言为:

  /*只设置一个值的语法*/
  transform-origin: x-offset
  transform-origin:offset-keyword
  /*设置两个值的语法*/
  transform-origin:x-offset y-offset
  transform-origin:y-offset x-offset-keyword
  transform-origin:x-offset-keyword y-offset
  transform-origin:x-offset-keyword y-offset-keyword
  transform-origin:y-offset-keyword x-offset-keyword
  /*设置三个值的语法*/
  transform-origin:x-offset y-offset z-offset
  transform-origin:y-offset x-offset-keyword z-offset
  transform-origin:x-offset-keyword y-offset z-offset
  transform-origin:x-offset-keyword y-offset-keyword z-offset
  transform-origin:y-offset-keyword x-offset-keyword z-offset

  transform-origin属性值可以是百分比、em、px等具体的值,也可以是top、right、bottom、left和center这样的关键词。默认值为50%,50%,0。

    • x-offset:用来设置transform-origin水平方向X轴的偏移量,可以使用值,同时也可以是正值(从中心点沿水平方向X轴向右偏移量),也可以是负值(从中心点沿水平方向X轴向左偏移量)。
    •  offset-keyword:是toprightbottomleftcenter中的一个关键词,可以用来设置transform-origin的偏移量。
    •  y-offset:用来设置transform-origin属性在垂直方向Y轴的偏移量,可以使用值,同时可以是正值(从中心点沿垂直方向Y轴向下的偏移量),也可以是负值(从中心点沿垂直方向Y轴向上的偏移量)。
    •  x-offset-keyword:是leftrightcenter中的一个关键词,可以用来设置transform-origin属性值在水平X轴的偏移量。
    •  y-offset-keyword:是topbottomcenter中的一个关键词,可以用来设置transform-origin属性值在垂直方向Y轴的偏移量。
    •  z-offset:用来设置3D变形中transform-origin远离用户眼睛视点的距离,默认值z=0,其取值可以,不过在这里将无效。

  transform-origin属性值可以是百分比、em、px等具体的值,也可以是top、right、bottom、left和center这样的关键词。默认值为50%,50%,0。

2、transform-style:指定嵌套元素如何在3D空间中呈现。

  有两个属性值:flatpreserve-3d。其中flat值为默认值,表示所有子元素在2D平面呈现。preserve-3d表示所有子元素在3D空间中呈现。

  如果对一个元素设置了transform-style的值为flat,则该元素的所有子元素都将被平展到该元素的2D平面中进行呈现。沿着X轴或Y轴方向旋转该元素将导致位于正或负Z轴位置的子元素显示在该元素的平面上,而不是它的前面或者后面。如果对一个元素设置了transform-style的值为preserve-3d,它表示不执行平展操作,他的所有子元素位于3D空间中。transform-style属性需要设置在父元素中,并且高于任何嵌套的变形元素。

  即transform-style的值为flat时,其子元素并不会受到rotateX等的影响,而是直接与父元素叠加在一起,和父元素处于同一平面上。当值为preserve-3d时,子元素与父元素分离,受单独的属性控制。

  有一点需要注意,如果你的元素设置了transform-style值为preserve-3d,就不能为了防止子元素溢出容器而设置overflow值为hidden,如果设置了overflow:hidden同样可以迫使子元素出现在同一平面(和元素设置了transform-styleflat一样的效果)。

3、perspective:对于3D变换最重要的属性,意思为透视,透视的。

  在两维的平面上利用线和面趋向会合的视错觉原理刻画三维物体的艺术表现手法。

  透视图:在人与建筑物之间设立一个透明的铅垂面K作为投影面,人的视线(投射线)透过投影面而与投影面相交所得的图形,称为透视图,或称为透视投影,简称透视。根据透视的原理绘制的图,多用于机械工程和建筑工程。

  透视的产生:因为有了光我们才得以看到自然界中的一切,这个过程就是光线照射到物体上并通过眼球内水晶体把光线反射到我们眼内视网膜上而形成图像,我们把光线在眼球水晶体的折射焦点叫做视点,视网膜上所呈现的图像称为画面。只是人脑通过自身的机能处理将倒过来的图像转换成正立图像。如果我们在眼前假定一个平面或放置一透明平面,以此来截获物体反射到眼球内的光线,就会得到与实物一致的图像,这个假定平面,也就是我们平时画画的画面。

  相关术语:

基面 形体所在的水平面,用字母G表示。基面相当于三投影面体系中的水平投影面H。
画面 透视图所在的平面,一般为铅垂面,用字母P表示。也可以用倾斜平面做画面。
基线 基面与画面的交线,用字母gl表示。
视点 观看者眼睛所在的位置,用字母S表示。
站点 观看者站定的位置,即视点S的基面上的正投影,用E表示。
心点 视点S在画面上的正投影,用字母Vc表示。
主视线 垂直于画面P的视线,也就是过视点S和心点Vc的直线。也叫中心视线
平面 过视点S的水平面。

  可分为一点透视、两点透视、三点透视。

  上面介绍了透视的相关知识,现在开始是正题。

  perspective属性会设置查看者的位置,并将可视内容映射到一个视锥上,继而投到一个2D视平面上。如果不指定透视,则Z轴空间中的所有点将平铺到同一个2D视平面中,并且变换结果中将不存在景深概念。

  我们可以简单的理解为视距,用来设置用户和元素3D空间Z平面之间的距离。而其效应由他的值来决定,值越小,用户与3D空间Z平面距离越近,视觉效果更令人印象深刻;反之,值越大,用户与3D空间Z平面距离越远,视觉效果就很小。

  在3D变形中,对于某些变形,perspective属性对于查看变形的效果来说必不可少。

  perspective属性包括两个属性:none和具有单位的长度值。其中perspective属性的默认值为none,表示无限的角度来看3D物体,但看上去是平的。另一个值接受一个长度单位大于0的值。而且其单位不能为百分比值。值越大,角度出现的越远,从而创建一个相当低的强度和非常小的3D空间变化。反之,此值越小,角度出现的越近,从而创建一个高强度的角度和一个大型3D变化。

  比如你站在10英尺和1000英尺的地方看一个10英尺的立方体。在10英尺的地方,你距离立方体是一样的尺寸。因此视角转变远远大于站在1000英尺处的,立体尺寸是你距离立方体距离的百分之一。同样的思维适用于perspective值。

  依据上面的介绍,我们可对perspective取值做一个简单的结论:

  •  perspective取值为none或不设置,就没有真3D空间。
  •  perspective取值越小,3D效果就越明显,也就是你的眼睛越靠近真3D。
  •  perspective的值无穷大,或值为0时与取值为none效果一样。

  为了更好的理解perspective属性,我们很有必要把他和translateZ的关系结合起来。其实也可以把perspective的值简单的理解为人的眼睛到显示器的距离,而translate就是3D物体距离源点的距离,下面引用w3cplus的一张图来解说perspectivetranslateZ的关系。

  上图显示了perspective属性和translateZ的位置比例。要顶部的图,Z是半个d,为了使用原始圆(轮廓)看起来出现在Z轴上(虚线圆),画布上的实体圆将扩大两部,如浅蓝色的圆。在底部图中显示,圆按比例缩小,致使虚线圆出现在画布后面,并且z的大小是距原始位置三分之一。

  perspective是针对父元素的,设置人眼与父元素间距离,父元素可以理解为子元素的投影处,即父元素为子元素的画布。translateZ则是设置子元素与画布的距离的,距离的单位为像素。比方说,一个1680像素宽的显示器中有张美女图片,应用了3D transform,同时,该元素或该元素父辈元素设置的perspective大小为2000像素。则这张美女多呈现的3D效果就跟你本人在1.2个显示器宽度的地方(1680*1.2≈2000)看到的真实效果一致!!

  我们都知道近大远小的道理,对于没有rotateX以及rotateY的元素,translateZ的功能就是让元素在自己的眼前或近或远。比方说,我们设置元素perspective为201像素,则其子元素,设置的translateZ值越小,则子元素大小越小(因为元素远去,我们眼睛看到的就会变小);translateZ值越大,该元素也会越来越大,当translateZ值非常接近201像素,但是不超过201像素的时候(如200像素),该元素的大小就会撑满整个屏幕(如果父辈元素没有类似overflow:hidden的限制的话)。因为这个时候,子元素正好移到了你的眼睛前面,所谓“一叶蔽目,不见泰山”,就是这么回事。当translateZ值再变大,超过201像素的时候,该元素看不见了——这很好理解:我们是看不见眼睛后面的东西的!

  关于Chrome浏览器以及透视盲区:
  在Chrome浏览器下,要想看到完整的3D效果,还需要3D变换元素正好在窗体的垂直居中位置。

  透视盲区不难理解,假设前面一排门,每个门都是1米,你距离门2米,显示,当所有门都开了45°角的时候,此时,距离中间门右侧的第二个门正好与你的视线平行,这个门的门面显然就什么也看不到。这就是为什么上面右侧第三个门一片空白的元素——特定的视角以及距离形成的视觉盲区。

  在3D变形中,除了perspective属性可以激活一个3D空间之外,在3D变形的函数中的perspective()也可以激活3D空间。他们不同的地方是:perspective用在舞台元素上(变形元素们的共同父元素);perspective()就是用在当前变形元素上,并且可以与其他的transform函数一起使用。

  虽然perspective属性和perspective()函数所起的功能是一样的,但其取值以及以运用的对像有所不同:

    •  perspective属性可以取值为none或长度值;而perspective()函数取值只能大于0,如果取值为0或比0小的值,将无法激活3D空间;
    •  perspective属性用于变形对像父元素;而perspective()函数用于变形对像自身,并和transform其他函数一起使用。

4、perspective-origin:

  3D变形中另一个重要属性,主要用来决定perspective属性的源点角度。它实际上设置了X轴和Y轴位置,在该位置观看者好像在观看该元素的子元素。

  perspective-origin:[<percentage> | <length> | left | center | right | top | bottom] | [[<percentage> | <length> | left | center | right] && [<percentage> | <length> | top | center | bottom]] 

  该属性的默认值为“50% 50%”(也就是center),其也可以设置为一个值,也可以设置为两个长度值。

  •  第一个长度值指定相对于元素的包含框的X轴上的位置。它可以是长度值(以受支持的长度单位表示)、百分比或以下三个关键词之一:left(表示在包含框的X轴方向长度的0%),center(表示中间点),或right(表示长度的100%)。
  •  第二个长度值指定相对于元素的包含框的Y轴上的位置。它可以是长度值、百分比或以下三个关键词之一:top(表示在包含框的Y轴方向长度的0%),center(表示中间点),或bottom(表示长度的100%)。

  注意,为了指转换子元素变形的深度,perspective-origin属性必须定义父元素上。通常perspective-origin属性本身不做任何事情,它必须被定义在设置了perspective属性的元素上。换句话说,perspective-origin属性需要与perspective属性结合起来使用,以便将视点移至元素的中心以外位置。

  往往我们看一样东西不可能一直都在中心位置看,想换个角度,换个位置一看究竟,这个时候就离不开perspective-origin这个属性,下面来自于W3C官网的图可以简单阐述这一观点:

  接下来的示例演示了修改perspective-origin的属性值对立方体的影响:

  介绍了这么多复杂的属性了,介绍一个简单的歇歇脚。

5、backface-visibility

  很简单的一个属性,visible | hidden两个值可选,相当于是否使元素透明,透明的时候即visible,在转至背面时,也可以看到内容,内容是反的。hidden既不可见。

  一个元素的可见性与“backface-visibility:hidden”决定如下:

  •  元素在3D环境下渲染上下文,将根据3D变形矩阵来计算,反之元素不在3D环境下渲染上下文,将根据2D变形矩阵来计算。
  •  如果组件的矩阵在第3行、3列是负值,那么元素反面是隐藏,反之是可见的。

  简单点来说,backface-visibility属性可用于隐藏内容的背面。默认情况下,背面可见,这意味着即使在翻转后,旋转的内容仍然可见。但当backface-visibility设置为hidden时,旋转后内容将隐藏,因为旋转后正面将不再可见。该功能可帮助您模拟多面的对象,您可以轻松确保只有正面可见。

  上述内容转自:http://www.w3cplus.com/css3/transform-basic-property.html。

   顺便安利一篇文章,关于覆盖内容的知识,CSS Overlay技巧。

  介绍完转换的一些属性,就要开始研究两个主要的变换方法了,matrix()和matrix3d()。

6、matrix

  该方法有六个参数,matrix(a,b,c,d,e,f),对应的转换关系为:

CSS3中矩阵位置计算公式 张鑫旭-鑫空间-鑫生活

  一个很简单的矩阵变换。

  根据数学方面的知识,可以得出:

  translate(x,y)=matrix(1,0,0,1,x,y)

  scale(x,y)=matrix(x,0,0,y,0,0)

  rotate(θdeg)=matrix(cosθ,sinθ,-sinθ,cosθ,0,0)-证明方法:根据中心旋转证明,详细参考解析几何。

  skew(θxdeg,θydeg)=matrix(1,tan(θy),tan(θx),1,0,0)-原理:skew是在保证图形在某一个坐标轴上距离不变的情况下,对另外一条坐标轴做倾斜,所以可推出上面的公式。

  还有一个只能通过matrix实现的,比如说:

  镜面翻转matrix(-1,0,0,1,0,0)

  沿y=kx对称:matrix((1-k*k) / (1+k*k), 2k / (1 + k*k), 2k / (1 + k*k), (k*k - 1) / (1+k*k), 0, 0)。

  证明方法可以参考数学类里面的内容。

  但是matrix还是有所限制的,比如矩形映射为梯形,使用矩阵变换实现不了,因为原来平行的线,在通过矩阵变换后仍然平行。

7、matrix3d

  要想实现矩形变换,还是要借助matrix3d。

  matrix3d比2d情况下多了z轴,参数也相应的变为了十六个:matrix3d(n1,n2,n3,n4,n5,n6,n7,n8,n9,n10,n11,n12,n13,n14,n15,n16),矩阵形式为:

  可以看到,比2D情况下多了很多参数,特别是最后一行,坐标只有三个点,最后一行是什么呢?很明显,前面的参数里有个透视,最后一个参数就是透视。

  translate3d(x,y,z)=matrix3d(1,0,0,x,0,1,0,y,0,0,0,1,z,0,0,0,1)

  scale3d(x,y,z)=matrix3d(x,0,0,0,0,y,0,0,0,0,z,0,0,0,0,1)

  关于旋转参考:三维旋转矩阵的推导。

  rotate3d(x,y,z,angle);略微麻烦。在3D空间,旋转有三个程度的自由来描述一个转动轴。轴的旋转是由一个[x,y,z]向量并经过元素原点。

  •  x:是一个0到1之间的数值,主要用来描述元素围绕X轴旋转的矢量值;
  •  y:是一个0到1之间的数值,主要用来描述元素围绕Y轴旋转的矢量值;
  •  z:是一个0到1之间的数值,主要用来描述元素围绕Z轴旋转的矢量值;
  • angle:是一个角度值,主要用来指定元素在3D空间旋转的角度,如果其值为正值,元素顺时针旋转,反之元素逆时针旋转。

    三个旋转函数功能等同:

  •  rotateX(a)函数功能等同于rotate3d(1,0,0,a)
  •  rotateY(a)函数功能等同于rotate3d(0,1,0,a)
  •  rotateZ(a)函数功能等同于rotate3d(0,0,1,a)

  最后说明一下,上面这些变形都是可以叠加的,叠加的效果之间用空格隔开。

  这些矩阵在数学上叫做变换矩阵。关于3D变换更好的说明,可以查看matrix3d

 

  本文以上内容取自http://www.zhangxinxu.com与http://www.w3cplus.com特此鸣谢


推荐阅读
  • 作为一名CSS初学者,我在博客园中尝试通过CSS美化页面,特别是为超链接添加图标,以提升阅读体验。本文将分享如何使用CSS和字体图标库来实现这一功能。 ... [详细]
  • 本文介绍了JSP的基本概念、常用标签及其功能,并通过示例详细说明了如何在JSP页面中使用Java代码。 ... [详细]
  • BeautifulSoup4 是一个功能强大的HTML和XML解析库,它能够帮助开发者轻松地从网页中提取信息。本文将介绍BeautifulSoup4的基本功能、安装方法、与其他解析工具的对比以及简单的使用示例。 ... [详细]
  • 在创建带有左侧图标的按钮时,遇到了文本与图标对齐的问题。本文提供了几种使用Bootstrap 4解决此问题的方法。 ... [详细]
  • 为何第三个div会影响其他两个div?
    探讨了在使用内联块(inline-block)元素布局时,第三个div如何影响前两个div的位置,并提供了具体的解决方案。 ... [详细]
  • 本文探讨了如何通过优化 DOM 操作来提升 JavaScript 的性能,包括使用 `createElement` 函数、动画元素、理解重绘事件及处理鼠标滚动事件等关键主题。 ... [详细]
  • 本文探讨了在一个物理隔离的环境中构建数据交换平台所面临的挑战,包括但不限于数据加密、传输监控及确保文件交换的安全性和可靠性。同时,作者结合自身项目经验,分享了项目规划、实施过程中的关键决策及其背后的思考。 ... [详细]
  • 本文探讨了在使用Apache Flink向Kafka发送数据过程中遇到的事务频繁失败问题,并提供了详细的解决方案,包括必要的配置调整和最佳实践。 ... [详细]
  • 使用CSS与HTML构建动态图片墙
    本文介绍如何利用CSS和HTML创建一个动态响应的图片墙,特别适合在Firefox和Chrome浏览器中查看。通过简单的鼠标交互,用户可以放大浏览图片。 ... [详细]
  • 本文深入探讨了HTML5中十五个重要的新特性,为开发者提供了详细的指南。 ... [详细]
  • CSS技巧:创建带有背景图的按钮
    本文详细探讨了使用CSS创建带有背景图片的按钮的方法,并提供了具体的实例代码,帮助开发者解决实际开发中的相关问题。 ... [详细]
  • 本文通过具体示例详细介绍了 Python 中的装饰器和装饰类的使用方法,包括带参数的装饰器和装饰类的应用场景。 ... [详细]
  • 视觉Transformer综述
    本文综述了视觉Transformer在计算机视觉领域的应用,从原始Transformer出发,详细介绍了其在图像分类、目标检测和图像分割等任务中的最新进展。文章不仅涵盖了基础的Transformer架构,还深入探讨了各类增强版Transformer模型的设计思路和技术细节。 ... [详细]
  • 深入探讨前端代码优化策略
    本文深入讨论了前端开发中代码优化的关键技术,包括JavaScript、HTML和CSS的优化方法,旨在提升网页加载速度和用户体验。 ... [详细]
  • 本文介绍如何使用JavaScript中的for循环来创建一个九九乘法表,适合初学者学习循环结构的应用。 ... [详细]
author-avatar
失和孔洞_943
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有