@TOC
组件都了解的差不多了,下面就是页面整体布局设计了。在HTML中,使用的是DIV + CSS的布局方式,也可以用在小程序里。不过因为移动端的分辨率不统一,使得布局的自适应十分重要。所以研究一下CSS3,从 FlexBox (弹性盒子) 的伸缩布局开始。
CSS3 弹性盒是一种当页面需要适应不同的屏幕大小以及设备类型时确保元素拥有恰当的行为的布局方式。引入弹性盒布局模型的目的是提供一种更加有效的方式来对一个容器中的子元素进行排列、对齐和分配空白空间。
弹性盒子由弹性容器(Flex container)和弹性子元素(Flex item)组成。
弹性容器通过设置 display 属性的值为 flex 或 inline-flex将其定义为弹性容器。弹性容器内包含了一个或多个弹性子元素。弹性容器外及弹性子元素内是正常渲染的。弹性盒子只定义了弹性子元素如何在弹性容器内布局。弹性容器有主轴线和侧轴线,主轴线默认是行,即横向。弹性子元素按照主轴排列。
在以往的HTML中,因为代码格式布局的缘故,使得标签之间会有空格、回车等,这会在呈现时占用字符。而再弹性盒子中,这些空格不会再占用字符。
flex-direction: row | row-reverse | column | column-reverse 弹性子元素在父容器中的位置,即弹性容器主轴线的排列方向
justify-content: flex-start | flex-end | center | space-between | space-around 内容对齐,设置弹性子元素沿着弹性容器的主轴线对齐的方式(在弹性子元素没有占满主轴线时有效)
align-items: flex-start | flex-end | center | baseline | stretch 设置弹性子元素沿着弹性容器的副轴线对齐的方式
flex-wrap: nowrap | wrap | wrap-reverse | initial | inherit 设置弹性子元素的换行方式
align-content: flex-start | flex-end | center | space-between | space-around | stretch 用于修改 flex-wrap 属性的行为。类似于 align-items, 但它不是设置弹性子元素的对齐,而是设置各个行的对齐。
order:
margin: auto |
设置"margin"值为"auto"值,自动获取弹性容器中剩余的空间(包括主轴和侧轴)。
设置"margin-right"值为"auto"值,则将剩余的空间放置在元素的右侧(靠左对齐)。
align-self: auto | flex-start | flex-end | center | baseline | stretch 设置弹性元素自身在侧轴方向上的对齐方式
参数使用方式及效果同 align-items 。
flex是FlexBox最重要的属性了,使用这个属性可以自适应页面空间。
flex: auto | initial | none | inherit | [ flex-grow ] || [ flex-shrink ] || [ flex-basis ] 设置弹性子元素如何分配空间
这里对参数详细解释一下首先参数都是基于比率计算,计算公式为 各自子元素的flex参数值*(父容器主轴长度/各子元素flex值之和) ,意为将父容器的主轴平均分成子元素flex值之和份,每个子元素取其中flex值的份。打个比方一个父容器有4个子元素,每个子元素都是1,则每个子元素分1/4份。如果4个子元素中有1个值是2,则它分2/5,其他的分1/5。
那么 initial 计算值为 0 1 auto ,其意思就是当有剩余空间时按照0份的比率增长(即不增长),控件不足时按照1份的比率缩小,对其内容进行自适应。相应的 auto 、none 和指定参数就都能计算出来了。
一般在实际使用中,会将各元素的flex的值都设为1(或 auto ),则各元素尽量均分剩余的空间。区别在于由于内容长短的关系,无法均分时,flex 1 是较长的尺寸优先牺牲自己的尺寸,flex auto 是较长的尺寸优先扩展自己的尺寸。即 flex 1 结果为等比例均分, flex auto 结果为按照内容充分利用空间(比如文字多少不一)。
弹性盒子在HTML和小程序中都能使用,既然现在是在自学微信小程序开发,则在小程序里进行实例试验。首先定义下页面的结构,即页面上方一个固定高度区域用作标签栏,中间是自适应高度的内容区域,下方是固定高度的页脚区域。
<view class="root">
<view class="tabs">view>
<view class="content">view>
<view class="foot">view>
view>
/**index.wxss**/
/* 先设置页面高度,否则各下级区域是没有高度的 */
page{
height: 100%;
}
/* 设置根视图区域 */
.root{
display: flex; /* 设置为flex容器 */
height: 100%; /* 设置高度 */
background-color: wheat; /* 给个颜色,方便查看 */
flex-direction: column; /* 设置主轴为纵轴 */
}
/* 设置标签栏 */
.tabs{
background-color: chocolate; /* 给个颜色 */
height: 100rpx; /* 设置高度 */
}
/* 设置内容区域 */
.content{
flex: 1; /* 自适应剩余空间 */
background-color: darkgray; /* 给个颜色 */
}
/* 设置页脚区域 */
.foot{
height: 100rpx; /* 设置高度 */
background-color:#555; /* 给个颜色 */
}
主要结构设计好了,将标签栏细分为4个标签,且当前标签样式略有不同。
<view class="tabs">
<view class="item active">
<text>标签文本1text>
view>
<view class="item">
<text>标签文本2text>
view>
<view class="item">
<text>标签文本3text>
view>
<view class="item">
<text>标签文本4text>
view>
view>
/* 设置标签栏 */
.tabs{
background-color: chocolate; /* 给个颜色 */
display: flex; /* 设置为flex容器 */
flex-direction: row; /* 设置主轴横轴 */
}
/* 标签项 */
.tabs .item{
flex: 1; /* 等比例自适应空间 */
text-align: center; /* 内部文本对齐方式居中 */
font-size: 14px; /* 字体大小 */
background-color: #222; /* 背景颜色 */
color: #aaa; /* 字体颜色 */
padding: 8px; /* 内边距 */
}
/* 当前标签项 */
.tabs .item.active {
color:#fff; /* 文本颜色 */
border-bottom: 2px solid #e9232c; /* 下边框 */
}
为了多试验下学习成果,页脚部分使用个稍复杂的设计,类似QQ音乐等音乐播放器的播放栏。左侧是个专辑封面的图画,然后是歌曲、歌手名称,右侧是三个控制按钮。
<view class="foot">
<view class="pic">
<image src="../../images/poster.jpg">image>
view>
<view class="info">
<text class="title">歌曲名称text>
<text class="artist">歌手名字text>
view>
<view class="controls">
<image src="../../images/files.png">image>
<image src="../../images/play.png">image>
<image src="../../images/stop.png">image>
view>
view>
/* 设置页脚区域 */
.foot{
display: flex; /* 为了让信息区占用剩余空间,设置为flex容器 */
height: 100rpx; /* 设置高度 */
background-color:#555; /* 给个颜色 */
}
/* 页脚区域显示海报的image标签 */
.foot .pic image{
margin: 5px; /* 外边距 */
width: 80rpx; /* 宽 */
height: 80rpx; /* 高 */
}
/* 页脚区域的信息区 */
.foot .info{
flex: 1; /* 占用剩余空间 */
margin: 5px 1px; /* 外边距 */
}
/* 信息区的歌曲名称标题 */
.foot .info .title{
display: block; /* 因为有2个标签,是行内元素,所以排到了同一排。改成块元素。 */
font-size: 16px; /* 字体大小 */
color: #ccc; /* 字体颜色 */
}
/* 信息区的歌手名称 */
.foot .info .artist{
font-size: 12px; /* 字体大小 */
color: #aaa; /* 字体颜色 */
}
/* 控制区的三个按钮(标签) */
.foot .controls image{
width: 80rpx; /* 宽 */
height: 80rpx; /* 高 */
margin: 5px 2px; /* 外边距 */
}
既然页脚使用了音乐播放器的样式,那么内容区也使用音乐播放器的样式好了。内容区主要分3个区域,轮播图区,功能入口和歌单区。其中轮播图区先用一个图片代替,回头再做。功能入口区分为横向3部分,每部分由一个图片和一段文字组成。歌单区划分为2部分,分别是头部和内部。头部左侧是推荐歌单,右侧是更多。内部由多个单元组成,每个单元就是一个推荐歌单,由封面图片和描述文字两部分组成。
<view class="content">
<view class="slide">
<image src="../../images/01.jpg">image>
view>
<view class="portals">
<view class="item">
<image src="../../images/portal01.png">image>
<text>私人FMtext>
view>
<view class="item">
<image src="../../images/portal02.png">image>
<text>每日歌曲推荐text>
view>
<view class="item">
<image src="../../images/portal03.png">image>
<text>云音乐新歌榜text>
view>
view>
<view class="list">
<view class="title">
<view class="recommended">
<image src="../../images/ListTitle.png">image>
<text >推荐歌单text>
view>
<view class="blank">view>
<view class="more">
<text>更多>>text>
view>
view>
<view class="inner">
<view class="item">
<image src="../../images/poster.jpg">image>
<text>歌单名称text>
view>
<view class="item">
<image src="../../images/poster.jpg">image>
<text>歌单名称text>
view>
<view class="item">
<image src="../../images/poster.jpg">image>
<text>歌单名称text>
view>
<view class="item">
<image src="../../images/poster.jpg">image>
<text>歌单名称text>
view>
<view class="item">
<image src="../../images/poster.jpg">image>
<text>歌单名称text>
view>
<view class="item">
<image src="../../images/poster.jpg">image>
<text>歌单名称text>
view>
view>
view>
view>
/* 设置内容区域 */
.content{
flex: 1; /* 自适应剩余空间 */
background-color: darkgray; /* 给个颜色 */
}
/* 内容区域的轮播区 */
.content .slide image{
height: 250rpx; /* 高 */
width: 100%; /* 宽 */
}
/* 功能入口区 */
.content .portals{
display: flex; /* 为了让子元素均分空间,设置为flex容器 */
}
/* 功能入口的每个单元 */
.content .portals .item{
flex: 1; /* 等比例自适应空间 */
}
/* 每个单元的图片 */
.content .portals .item image{
width: 120rpx; /* 宽 */
height: 120rpx; /* 高 */
display: block; /* 显示为块元素 */
margin: 10px auto; /* 外边距 */
}
/* 每个单元的文本 */
.content .portals .item text{
font-size: 12px; /* 文字大小 */
text-align: center; /* 文字居中 */
display: block; /* 显示为块元素 */
}
/* 歌单列表区域 */
.content .list{
display: flex; /* 为了让内部区域占用剩余空间,设置为flex容器 */
flex-direction: column; /* 设置主轴为纵轴 */
}
/* 歌单区上部 */
.content .list .title{
display: flex; /* 为了让空白区域占用剩余空间,设置为flex容器 */
}
/* 上部的推荐区 */
.content .list .title .recommended{
display: flex; /* 为了方便调整对齐推荐区内的图片和文本,设置为flex容器 */
margin: 5px 5px; /* 外边距 */
}
/* 推荐区的图片 */
.content .list .title .recommended image{
height: 30px; /* 高 */
width: 30px; /* 宽 */
}
/* 推荐区的文本 */
.content .list .title .recommended text{
display: block; /* 显示为块元素 */
margin: auto 0; /* 外边距 */
font-size: 14px; /* 字体大小 */
}
/* 推荐区中间的空白处 */
.content .list .title .blank{
flex: 1; /* 获取剩下所有空间 */
}
/* 推荐区右侧的更多 */
.content .list .title .more{
font-size: 14px; /* 字体大小 */
margin: auto 5px; /* 外边距 */
}
/* 歌单区的内容区 */
.content .list .inner{
display: flex; /* 为了让子元素更好的分部排列,设置为flex容器 */
flex-wrap: wrap; /* 内部子元素超出部分自动换行 */
justify-content:space-around; /* 子元素沿主轴空空间环绕对齐 */
}
/* 内容区的单元 */
.content .list .inner .item{
/* 这里不用flex: 1;是因为如果改变机型使得行分辨率改变了,因为图片宽是固定的且居中了,文本因为靠左就会超出图片 */
margin-bottom: 3px; /* 下方外边距 */
}
/* 内容区每个单元的图片 */
.content .list .inner .item image{
height: 120px; /* 高 */
width: 120px; /* 宽 */
display: block; /* 显示为块元素 */
margin: 0 auto; /* 外边距 */
}
/* 内容区每个单元的文本 */
.content .list .inner .item text{
display: block; /* 显示为块元素 */
font-size: 14px; /* 字体大小 */
}
这样内容区域就设计完成了,但是返回查看时发现,因为内容区域的元素撑大了区域,使得页脚区域在页面下,所以需要再进行调整。
为了固定页脚区域,可以将内容区域设置滚动条,使得内容区域超出部分使用滚动条查看。这里有2种方法。
/* 设置内容区域 */
.content{
flex: 1; /* 自适应剩余空间 */
background-color: darkgray; /* 给个颜色 */
overflow: scroll; /* 超出部分使用滚动条 */
}
<scroll-view class="content" scroll-y>
scroll-view>
.content{
flex: 1; /* 自适应剩余空间 */
background-color: darkgray; /* 给个颜色 */
overflow: hidden; /* 超出部分设置隐藏 */
}
小程序提供了轮播标签
<swiper interval="6000" duration="600" indicator-dots autoplay >
<swiper-item>
<view class="slide">
<image src="../../images/01.jpg">image>
view>
swiper-item>
<swiper-item>
<view class="slide">
<image src="../../images/02.jpg">image>
view>
swiper-item>
<swiper-item>
<view class="slide">
<image src="../../images/03.jpg">image>
view>
swiper-item>
swiper>