平面转换
CSS3中动画效果包括3个部分:过渡(transition
)、变形(transform
)、动画(animation
)。前面学习的CSS过渡(transition
)呈现的是一个“过程”,而CSS变形(transform
)呈现的仅仅是一个“结果”。
使用transform属性来实现元素的变形效果,变形分为平面转换和空间转换。
语法:
transform:属性;
平面转换具有四个属性
属性 | 功能 |
---|---|
translate() | 平移 |
scale() | 缩放 |
skew() | 倾斜 |
rotate() | 旋转 |
平移
语法:
transform: translateX(x); /*沿X轴方向平移*/
transform: translateY(y); /*沿Y轴方向平移*/
transform: translate(x, y); /*沿X轴和Y轴同时平移*/
x和y取值:
- 像素单位数值
- 百分比(参照物为盒子自身尺寸)
translate()
如果只给出一个值, 表示x轴方向移动距离
利用百分比绝对定位居中:
<style>
div{
position: absolute;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
}
</style>
案例:双开门
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
* {
margin: 0;
padding: 0;
}
.box {
width: 366px;
height: 200px;
margin: 0 auto;
background-color: yellow;
/* 使用transform后,会超出范围,使用overflow隐藏 */
overflow: hidden;
}
/* 两个可以连写在一起,并集 */
.box::before{
/* 使用平移可以忽略左右浮动影响 */
float: left;
content: '';
width: 50%;
height: 600px;
background-color: blue;
transition: all 1s;
}
.box::after {
/* 使用平移可以忽略左右浮动影响 */
float: right;
content: '';
width: 50%;
height: 600px;
background-color: red;
transition: all 1s;
}
.box::after {
background-position: right 0;
}
.box:hover::before {
/* 区别: width: 0是直接消失,而transform是平移,这里没放图片看不出来*/
width: 0;
}
.box:hover::after {
transform: translateX(100%);
}
</style>
</head>
<body>
<div class="box">
</div>
</body>
</html>
缩放
语法:
transform: scaleX(x); /*沿X轴方向缩放*/
transform: scaleY(y); /*沿Y轴方向缩放*/
transform: scale(x, y); /*沿X轴和Y轴同时缩放*/
x和y表示的值为缩放的倍数, scale值大于1表示放大, scale值小于1表示缩小 。如transform:scaleX(1.5)
;表示元素在x轴方向放大为原来的1.5倍。transform:scaleX(0.5)
;表示元素会在x轴方向缩小为原来的0.5倍。
倾斜
语法:
transform: skewX(x); /*沿X轴方向倾斜*/
transform: skewY(y); /*沿Y轴方向倾斜*/
transform: skew(x, y); /*沿X轴和Y轴同时倾斜*/
x和y表示的值倾斜的度数。
参数x表示元素在x轴方向的倾斜度数,单位为deg(即degree的缩写)。如果度数为正,则表示元素沿x轴方向逆时针倾斜;如果度数为负,则表示元素沿x轴方向顺时针倾斜。
参数y表示元素在y轴方向的倾斜度数,单位为deg。如果度数为正,则表示元素沿y轴方向顺时针倾斜;如果度数为负,则表示元素沿y轴方向逆时针倾斜。
旋转
语法:
transform: rotate(angle);
参数angle
表示元素相对于中心原点旋转的度数,单位为deg。如果度数为正,则表示顺时针旋转;如果度数为负,则表示逆时针旋转。
transform-origin属性改变转换原点
默认情况下,CSS3的各种平移、缩放等操作都是以元素的中心原点进行变形的,我们可以使用transform-origin
属性来改变元素的中心原点。
语法:
transform-origin: 原点水平位置 原点垂直位置;
取值:
关键字 | 百分比 | 说明 |
---|---|---|
top left | 0 0 | 左上 |
top center | 50% 0 | 靠上居中 |
top right | 100% 0 | 右上 |
left center | 0 50% | 靠左居中 |
center center | 50% 50% | 正中 |
right center | 100% 50% | 靠右居中 |
bottom left | 0 100% | 左下 |
bottom center | 50% 100% | 靠下居中 |
bottom right | 100% 100% | 右下 |
transform复合属性
变形中多种效果可以复合使用,如旋转会改变网页元素的坐标轴向,先写旋转,则后面的转换效果的轴向以旋转后的轴向为准,会影响转换结果,建议先写平移再写旋转。
案例:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>多重转换</title>
<style>
.box {
width: 800px;
height: 200px;
border: 1px solid #000;
}
.box div {
width: 200px;
height: 200px;
background-color: pink;
transition: all 3s;
}
.box:hover div {
/* 边走边转 */
transform: translate(600px) rotate(360deg);
/* 旋转可以改变坐标轴向 ,先旋转改变了坐标轴向,再移动距离*/
/* transform: rotate(360deg) translate(600px); */
/* 层叠性,相同属性 */
/* transform: translate(600px); */
/* transform: rotate(360deg); */
}
</style>
</head>
<body>
<div class="box">
<div></div>
</div>
</body>
</html>
空间转换
空间位移
网页里面的空间坐标系:
语法:
transform: translate3d(x, y, z);
transform: translateX(值);
transform: translateY(值);
transform: translateZ(值);
x,y,z的取值像素单位数值和百分比都可以。
我们设置了空间属性,却看不到有空间的变化,这就需要perspective
(透视)属性来实现透视效果。
默认情况下,无法观察到Z轴位移效果,因为Z轴是视线方向,移动效果应该是距离的远或近, 电脑屏幕是平面,默认无法观察远近效果,perspective
(透视)属性可以实现近大远小、近清楚远模糊的视觉效果。
注意perspective
属性是添加给父级的
语法:
perspective: 属性值;
取值:像素单位数值, 数值一般在800 – 1200
说明:属性值表示的含义是透视距离,也称为视距,就是人的眼睛到屏幕的距离。所以取值不能太大也不能太小。
空间旋转
语法:
transform: rotateZ(值);
transform: rotateX(值);
transform: rotateY(值)
左手法则 : 判断旋转方向: 左手握住旋转轴, 拇指指向正值方向, 手指弯曲方向为旋转正值方向。
呈现立体图形
上面我们使用了perspective透视属性让页面有了近大远小、近实远虚的视觉效果。但是并不能能呈现立体图形,我们需要使用transform-style: preserve-3d
才能使子元素处于真正的3d空间。
步骤
- 盒子父元素添加
transform-style: preserve-3d;
- 按需求设置子盒子的位置(位移或旋转)
3D导航案例:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>3D导航</title>
<style>
ul {
margin: 0;
padding: 0;
list-style: none;
}
.navs {
width: 300px;
height: 40px;
margin: 50px auto;
}
.navs li {
position: relative;
float: left;
width: 100px;
height: 40px;
line-height: 40px;
transition: all .5s;
transform-style: preserve-3d;
}
.navs li a {
position: absolute;
left: 0;
top: 0;
display: block;
width: 100%;
height: 100%;
text-align: center;
text-decoration: none;
color: #fff;
}
.navs li a:first-child {
background-color: green;
transform: translateZ(20px);
}
.navs li a:last-child {
background-color: orange;
transform: translateY(-20px) rotateX(90deg);
}
.navs li:hover {
transform: rotateX(-90deg);
}
</style>
</head>
<body>
<div class="navs">
<ul>
<li>
<a href="#">首页</a>
<a href="#">Index</a>
</li>
<li>
<a href="#">登录</a>
<a href="#">Login</a>
</li>
<li>
<a href="#">注册</a>
<a href="#">Register</a>
</li>
</ul>
</div>
</body>
</html>
空间缩放
语法:
语法
transform: scaleX(倍数);
transform: scaleY(倍数);
transform: scaleZ(倍数);
transform: scale3d(x, y, z);
动画
动画属性
语法:
animation: 动画名称 持续时间 动画方式 延迟时间 动画次数 动画方向 执行完毕时状态;
animation
是复合属性,animation
的子属性为:
属性 | 说明 |
---|---|
animation-name | 动画定义的名称 |
animation-duration | 动画的持续时间 |
animation-timing-function | 动画的速率方式 |
animation-delay | 动画的延迟时间 |
animation-iteration-count | 动画的播放次数,infinite为无限循环 |
animation-direction | 动画的播放方向,正向还是反向 |
animation-fill-more | 执行完毕的状态, forwards:最后一帧状态 backwards:第一帧状态 |
animation-play-state | 暂停动画, paused为暂停,通常配合:hover使用 |
注意:
- 动画名称和动画时长必须赋值
- 取值不分先后顺序
- 如果有2个时间值,第一个时间表示动画时长,第二个时间表示延迟时间
实现动画步骤:
- 定义动画
- 调用动画
定义动画:
@keyframes 动画名
{
0%{}
……
100%{}
}
如果只有两种状态,也可以这样表示:
@keyframes mycolor
{
from{}
to{}
}
steps逐帧动画
逐帧动画即帧动画,将动画过程等分成N份,一般配合精灵图实现动画效果。
语法:
animation-timing-function: steps(N);
精灵动画制作步骤:
- 设置盒子尺寸是一张小图的尺寸,背景图为当前精灵图
- 改变背景图的位置(移动的距离就是精灵图的宽度)
- 添加速度曲线
steps(N)
,N与精灵图上小图个数相同 - 添加无限重复效果
案例走马灯:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
<style>
* {
padding: 0;
margin: 0;
}
li {
list-style: none;
}
.box {
width: 600px;
height: 112px;
border: 5px solid #000;
margin: 100px auto;
overflow: hidden;
}
.box div{
float: left;
width: 200px;
height: 112px;
background-color: pink;
text-align: center;
line-height: 112px;
}
.box ul {
width: 2000px;
animation: move 5s infinite linear;
}
.box li {
float: left;
}
/* 定义动画:位移, ul 左侧使用 x -1400 */
@keyframes move {
to {
/* -1400px只移动7张图片,结束瞬间:前三张在框内,正是下一次动画的开始瞬间,使所以不会重复 */
transform: translateX(-1400px);
}
}
/* 用户鼠标移入box,动画暂停 */
.box:hover ul {
animation-play-state: paused;
}
</style>
</head>
<body>
<div class="box">
<ul>
<div class="one">1</div>
<div class="two">2</div>
<div class="three">3</div>
<div class="four">4</div>
<div class="five">5</div>
<div class="six">6</div>
<div class="seven">7</div>
<!-- 第567移动的时候,显示区域不能留白 -->
<div class="one">1</div>
<div class="two">2</div>
<div class="three">3</div>
</ul>
</div>
</body>
</html>
多组动画
动画可以设置多个
语法:
animation:
动画1,
动画2,
动画n
;