响应式布局
一、 MediaQuery媒体查询
什么是媒体查询?
为不同尺寸的屏幕设定不同的CSS样式,主要用于移动端
代码示例:
<!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>
div {
width: 200px;
height: 400px;
}
/* 媒体查询 */
@media screen and (min-device-width:100px) and (max-device-width:200px) {
div {
background-color:red;
}
}
@media screen and (min-device-width:201px) and (max-device-width:300px) {
div {
background-color:yellow;
}
}
@media screen and (min-device-width:301px) and (max-device-width:400px) {
div {
background-color:blue;
}
}
@media screen and (min-device-width:401px) {
div {
background-color:yellowgreen;
}
}
</style>
</head>
<body>
<div>
<h1>一个盒子</h1>
</div>
</body>
</html>
效果截图:
@mdeia常用参数
width、height 浏览器可视宽度、高度
device-width 设备屏幕的宽度
decive-height 设备屏幕的高度
需求:根据不同的宽度显示不同个数的div盒子
<!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>
#div0 {
width: 100%;
}
#div0 div {
height: 200px;
float: left;
text-align: center;
line-height: 200px; /* 设置文字垂直居中 */
}
#div0 div:nth-child(1) {
background-color: red;
}
#div0 div:nth-child(2) {
background-color: yellow;
}
#div0 div:nth-child(3) {
background-color: blue;
}
/* 媒体查询 */
/* 一行显示3个div */
@media screen and (min-device-width:400px) {
#div0 div {
width: 33.3%;
}
}
/* 一行显示2个div */
@media screen and (min-device-width:200px) and (max-device-width:399px) {
#div0 div {
width: 50%;
}
}
/* 一行显示1个div */
@media screen and (min-device-width:100px) and (max-device-width:199px) {
#div0 div {
width: 100%;
}
}
</style>
</head>
<body>
<div id="div0">
<div>1</div>
<div>2</div>
<div>3</div>
</div>
</body>
</html>
效果截图:
媒体查询其他引入方式
1、style标签,写在style标签中,有条件的执行某个内部样式表
<style>
#div0 {
width: 100%;
}
#div0 div {
height: 200px;
float: left;
text-align: center;
line-height: 200px;
/* 设置文字垂直居中 */
}
#div0 div:nth-child(1) {
background-color: red;
}
#div0 div:nth-child(2) {
background-color: yellow;
}
#div0 div:nth-child(3) {
background-color: blue;
}
</style>
<style media="(min-device-width:400px)">
#div0 div {
width: 33.3%;
}
</style>
<style media="(min-device-width:200px) and (max-device-width:399px)">
#div0 div {
width: 50%;
}
</style>
<style media="(min-device-width:100px) and (max-device-width:199px)">
#div0 div {
width: 100%;
}
</style>
</head>
2、link引入,写在link标签中,有条件的引入外部样式表
mediaQuery.css
/* 媒体查询 */
/* 一行显示3个div */
@media screen and (min-device-width:400px) {
#div0 div {
width: 33.3%;
}
}
/* 一行显示2个div */
@media screen and (min-device-width:200px) and (max-device-width:399px) {
#div0 div {
width: 50%;
}
}
/* 一行显示1个div */
@media screen and (max-device-width:199px) {
#div0 div {
width: 100%;
}
}
mediaQuery.html
二 、flex弹性布局
概念:FlexiableBox即是弹性盒子,用来进行弹性布局,可以配合rem处理尺寸的适配问题
flex-direction
子元素在父元素盒子中的排列方式(父元素添加这属性)
注意:如果父元素的宽度设置较小,子元素的总宽度远远超出了父元素的宽度,那么子元素设置的宽度无效,会自动压缩来适应父元素;
flex-wrap
子元素在父元素盒子中是否换行/列(父元素添加这属性)
flex-flow
是flex-direction
和flex-wrap
属性的简写形式
形式:flex-flow:row wrap
justify-content
用来存在剩余空间时,设置为间距的方式 (父元素中设置)
align-items
设置单行flex元素在交叉轴上的默认对齐方式 (父元素中设置)
举例:
<!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>
.div0 {
width:700px;
height: 400px;
background-color: pink;
display: flex;
flex-wrap: wrap;
justify-content: space-around; /* 设置子元素的间隔 */
align-items: center;/* 单行对齐方式 */
/* align-content:center; */
}
.div0 div {
width: 200px;
height: 100px;
background-color: yellow;
margin-top: 10px;
}
</style>
</head>
<body>
<div class="div0">
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
</div>
</body>
</html>
align-content
设置多行flex元素在交叉轴上的默认对象方式
举例:
.div0 {
width:700px;
height: 400px;
background-color: pink;
display: flex;
flex-wrap: wrap;
justify-content: space-around; /* 设置子元素的间隔 */
/* align-items: center;单行对齐方式 */
align-content:center; /*多行对齐方式*/
}
其他属性 (子元素中设置)
flex-basis
设置子对象的基准值
值设置为px
<style>
.div0 {
width:400px;
height: 500px;
background-color: pink;
display: flex;
}
.div0 div {
width: 200px;
height: 200px;
background-color: yellow;
/* 设置子对象的基准值,意味着子对象的宽度为50px,之前所设的宽度200px失效*/
flex-basis: 50px;
}
</style>
</head>
<body>
<div class="div0">
<div>1</div>
<div>2</div>
</div>
</body>
值设置为%
.div0 div {
width: 200px;
height: 200px;
background-color: yellow;
/* 两个div占父元素宽度的百分之30,也就是 400*0.3=120px */
flex-basis: 30%;
}
分别用来设置不同div的宽度
.div0 div {
width: 200px;
height: 200px;
background-color: yellow;
}
.div0 div:nth-child(1) {
flex-basis: 30px;
}
.div0 div:nth-child(2) {
flex-basis: 50px;
}
注意:如果子元素设置了flex-basis
,那么它原先设置的宽度将失效
flex-grow
设置盒子的扩展比率
说人话就是,把父元素没有占满的宽度,子元素按照一定的份数去占满。
如flex-grow
设置值是数字,如果数字 >=1 则代表允许扩展;反之不允许
<style>
.div0 {
width: 400px;
height: 500px;
background-color: pink;
display: flex;
}
.div0 div {
width: 200px;
height: 200px;
background-color: yellow;
}
/*
父元素剩余的宽度:400-50-100=250px
250 / 5(1+4) = 50 每份占50px宽
第一个div宽度为 50px + 1*50px = 100px
第二个div宽度为 100px + 4*50px = 300px
*/
.div0 div:nth-child(1) {
flex-basis: 50px;
flex-grow: 1; /* 占空闲宽度的1份 */
}
.div0 div:nth-child(2) {
flex-basis: 100px;
flex-grow: 4; /* 占空闲宽度的4份 */
}
</style>
flex-grow 前提是的要有空余的宽度
flex-shrink
设置盒子的缩小比率
说人话就是,把超出的父元素的宽度,按照一定的比率去缩小,默认是是开启缩小的,我们可以设置flex-shrink:0;
代表不开启缩小,这样我们就可以看到超出父元素的区域
<style>
.div0 {
width: 400px;
height: 500px;
background-color: pink;
display: flex;
}
.div0 div {
width: 200px;
height: 200px;
background-color: yellow;
}
/* 缩小比率
超出父元素的宽度: 300+300-400=200px
200 / 5(1+4) = 40px
第一个div的宽度为 300px - 1*40px = 260px
第二个div的宽度为 300px - 4*40px = 140px
*/
.div0 div:nth-child(1) {
flex-basis: 300px;
flex-shrink: 1; /* 占超出区域的1份 */
}
.div0 div:nth-child(2) {
flex-basis: 300px;
flex-shrink: 4; /* 占超出区域的4份 */
}
</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>
.div0 {
width: 300px;
height: 30px;
background-color: rgb(238, 238, 238);
display: flex;
border: 1px solid gainsboro;
}
.div0 label {
flex: 1 1 20px; /* 允许扩展与缩小,每个label的宽度为20px */
text-align: center;
line-height: 30px;
}
.div0 input {
border: none; /* 去掉input边框 */
outline: none; /* 去掉input获取焦点的边框 */
}
</style>
</head>
<body>
<div class="div0">
<label>姓名</label>
<input type="text"/>
<label>Go</label>
</div>
</body>
</html>
三 、rem的使用方法
概念:指相对于根元素的字体大小的单位
区别:em相对于父级的字体大小的单位
案例:使用媒体查询+rem/js,实现 在不同宽度的视口下自动调整字体大小
<!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>
<script>
let c = () =>{
/* 获取设备的宽度 */
let w = document.documentElement.clientWidth;
/* 通过宽度设置字体 */
/* 默认情况下字体设置20px,可自己设置 320也是可自己设置,意思就是说在不同的设备宽度中动态的显示字体大小
这里最大的字号就是 40px
*/
let n = (20*(w/320) > 40 ? 40 + 'px' : (20*(w/320) + 'px'));
document.documentElement.style.fontSize = n;
}
/* 添加事件 */
// 1、初始事件
window.addEventListener("load",c)
// 2、当调整浏览器窗口大小时,发生 resize 事件
window.addEventListener("resize",c)
</script>
<style>
html {
font-size:10px;
}
div {
font-size: 1rem; /* 1rem = 10px */
}
</style>
</head>
<body>
<div>123</div>
</body>
</html>
自适应布局
不同的设备用不同的页面或局部伸缩
案例1:flex实现移动端三栏布局
<!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>
.div0 {
display: flex;
text-align: center;
}
.div0 div:first-child {
flex: 0 0 50px;
background-color: red;
}
.div0 div:nth-child(2) {
flex: 1 1 80%;
background-color: yellow;
}
.div0 div:last-child {
flex: 0 0 50px;
background-color: red;
}
/* 结合媒体查询更换背景颜色 */
@media screen and (min-device-width:400px) {
.div0 div:first-child , .div0 div:last-child{
background-color: blue;
}
}
@media screen and (min-device-width:300px) and (max-device-width:399px) {
.div0 div:first-child , .div0 div:last-child{
background-color: pink;
}
}
@media screen and (max-device-width:299px) {
.div0 div:first-child , .div0 div:last-child{
background-color: yellowgreen;
}
}
</style>
</head>
<body>
<div class="div0">
<div>1</div>
<div>2</div>
<div>3</div>
</div>
</body>
</html>
案例2:
<!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>
<link href="./css/big.css" rel="stylesheet" media="(min-device-width:1000px)">
</head>
<body>
<div class="layout">
<div class="top"></div>
<div class="main">
<div>
<li>分类1</li>
<li>分类2</li>
<li>分类3</li>
<li>分类4</li>
<li>分类5</li>
<li>分类6</li>
</div>
<div>
<li>图片</li>
<li>图片</li>
<li>图片</li>
<li>图片</li>
<li>图片</li>
<li>图片</li>
<li>图片</li>
<li>图片</li>
</div>
</div>
</div>
</body>
</html>
css/big.css
* {
margin: 0;
padding: 0;
background-color: #f5f5ff;
}
.layout {
display: flex;
width: 80%;
margin: 0 auto;
flex-direction: column; /* 主轴方向是纵向 */
}
.layout .top {
flex: 0 0 50px;
background-color: yellow;
margin-top: 10px;
}
.layout .main {
display: flex;
flex: 0 0 100%;
}
.layout .main div:nth-child(1) {
display: flex;
flex:0 0 10%;
flex-wrap: wrap;
}
.layout .main div:nth-child(1) li {
flex:0 0 100%;
height: 64px;
line-height: 64px;
text-align: center;
list-style-type: none; /* 去掉li前面的小圆点 */
border-left: 1px solid white;
border-right: 1px solid white;
border-bottom: 1px solid white;
}
.layout .main div:nth-child(2) {
display: flex;
flex:0 0 90%;
flex-wrap: wrap;
justify-content:flex-start ;
}
.layout .main div:nth-child(2) li {
flex:0 0 30%;
height: 120px;
text-align: center;
list-style-type: none; /* 去掉li前面的小圆点 */
background-color: yellow;
margin-top: 10px;
margin-right: 10px;
}
学习视频
慕课网: https://www.imooc.com/learn/1285