我写小程序像菜虚鲲——3、你能17张牌把我秒杀,我当场把电脑屏幕吃掉

5,542 阅读25分钟

标题和内容无关,只是前几天看卢姥爷的鬼畜:www.bilibili.com/video/av126…,顺带消费下,上柱香~

看上一节《我写小程序像菜虚鲲——2、鸡你太美》的人比预想中少很多哇…

可能是我不够骚了(或者发的时间不对),不过还是建议阅读下「逆向微信小程序」那部分内容。本节来肝下「微信小程序中布局」相关姿势点。希望你学完本章后,可以:根据设计尸给的设计稿,堆砌控件。本节内容较多,建议点赞收藏以后有时间再看,毕竟 收藏了≈我会了,本文姿势点安排如下:

  • 1、物理像素,设备独立像素,DPR,微信小程序特有尺寸rpx,设计稿尺寸;
  • 2、WXSS样式导入的几种方式;
  • 3、如何通过选择器定位到元素;
  • 4、文档流与脱离文档流;
  • 5、块级元素与行内元素,通过display属性转换;
  • 6、盒子模型,box-sizing,外边距合并问题;
  • 7、定位:相对定位,绝对定位,固定定位;
  • 8、浮动与清除浮动;
  • 9、多列布局multi-column,实现多列文本与简单图片瀑布流;
  • 10、flex弹性布局;
  • 11、布局实战:仿写每日优鲜首页。

0x1、微信小程序特有单位——rpx


px(pixel)像素,相信大家都不陌生吧,但是有三个名词要说下:

  • ① 「物理像素」:设备屏幕实际拥有的像素点,比如iPhone 6的分辨率为750*1334,代表水平方向有750个像素点,竖直方向有1334个像素点。
  • ②「设备独立像素」:可理解为反映在CSS/JS代码里像素点数。
  • ③「设备像素比(DPR)」:一个设备的物理像素与逻辑像素的比。

看到这里,读者可能会有疑问:为何像素还要分两种,有区别吗

答:很久以前是没区别的,在CSS里写1px,屏幕就渲染一个物理像素,即DPR=1。随着苹果Retina技术的出现,这种局面被打破,使用Retina技术可以使用多个物理像素来渲染一个逻辑像素,屏幕尺寸没变,分辨率变高了,而人的视网膜无法分辨出屏幕上的像素点,这也是感觉Retina屏却比非Retina屏细腻的原因。

在Retina屏上DPR不再是1,而是大于1,比如iPhone 6DPR=2,物理像素是:750x1334,对应的逻辑像素: (750x1334)/2 = 375x667

名词科普到这里,接着说回rpx(responsive pixel),微信小程序特有尺寸单位,可以根据「屏幕宽度进行自适应」,规定:小程序屏幕宽度为750rpx。可以简单地理解为:

把页面按比例分割为750份,而每一份的大小是1rpx。

然后iPhone 6的物理像素刚好为750*1334,所以在iPhone 6中:

1rpx = 1个物理像素(1px)

所以,如果设计尸以 iPhone 6 为标准画设计稿的话,标注是多少px,小程序就直接多少rpx,不用换算,而且还不用担心在各个平台上的适配情况,卧槽,美滋滋啊!!!最后总结下结论,不难得出这样的等式:

在iPhone 6中:1rpx = 0.5px逻辑像素 = 1物理像素


0x2、WXSS样式导入


关于CSS样式上节课就谈了,微信小程序中的WXSS稍微有点不一样。除了在目录下创建同名的.wxss文件会自动引用外。还可以使用@import语句 导入外部样式,相对路径,示例如下:

/* app.wxss */
@import './wxss/base.wxss';

除此之外,可以使用 style属性 设置内联样式,一般是接收 动态样式 用,而把 静态样式 统一写到class中,示例如下:

<view style="color:{{color}};" />

0x3、选择器定位元素


为元素设置样式,那你也得先定位到元素是吧!有如下三类最基础的选择器:

  • 标签选择器」:文档中 所有的特定标签 使用同一个CSS样式。
  • id选择器」:元素以 id属性 来设置id选择器,选择器以「#」来定义。
  • 类选择器」:元素以 class属性 来设置类选择器,可以在多个元素中使用,以「.」号显示。

接着是具体定位到元素的各种操作示例:

/* 标签选择器*/
p{color: red;}

/* id选择器 */
#id-choose {color: green;}

/* class选择器 */
.class-choose {color: blue;}

/* 对选择器进行分组,共享同一个样式,逗号隔开 */
text, button, checkbox { color: green; }
.text-1, .text-2 { color: gold }

/* x元素内所有的y元素,选择作为x元素后代的y元素,称后代选择器或包含选择器 */
view text{ color: purple }
/* 还可使用*通配符选择所有元素 */
view *{ color: purple }

/* 父元素为x元素中的所有y元素,又称:子元素选择器 */
view > text{ color: red }

/* x元素后的所有y元素,又称:相邻兄弟选择器 */
view + text{ color: red }

/* 选择前面有x元素的每个y元素 */
view ~ text{ color: red }

/* 还可以通过属性来定位元素 */
<view aria-role="button" aria-label="submit-label">提交</view>
[aria-role]{ color: purple }   /* 带有某属性 */
[aria-role="button"]{ color: purple }   /* 带某属性且等于xxx */
[aria-label~="label"]{color: purple}    /* 带某属性且包含XXX单词 */
[aria-label|="submit"]{color: purple}   /* 带某属性且XXX单词开头 */
[aria-label^="su"]{color: purple}   /* 带某属性且xx开头,不需要单词 */
[aria-label$="el"]{color: purple}   /* 带某属性且xx结尾,不需要单词 */
[aria-label*="el"]{color: purple}   /* 带某属性且包含xxx */
/* 还可以搭配元素选择器玩耍 */
view[aria-role]{ color: purple }

/* 伪类,根据顺序定位 */
.content-1 text:first-child{ color: pink }  /* 父元素首个x元素 */
.content-1 text:last-child{ color: pink }  /* 父元素最后一个x元素 */
.content-1 text:nth-child(n){ color: pink }  /* 父元素第n个x元素 */
.content-1 text:nth-last-child(n){ color: pink }  /* 父元素倒数第n个x元素 */

/* 伪元素 */
<view class="content">中间元素</view>
/* 元素前添加内容 */
.content:before{
  content: "插在前面的文字";
  color: red;
}
/* 元素后添加内容 */
.content:after {
  content:url("http://codingboy.xyz/avator.png");
}

注意一点!!!

wxss无法获取本地图片资源,可使用 网络图片base64后的图片image标签

再注意一点!!!

class属性值多个空格分隔,比如:<view class="font small blue">,其实就是指定多个class。这样写是为了CSS模块化设计减少CSS重复代码,提高复用性。比如小程序中文本有几种,样式是基本一样的,可能只是字体大小或颜色不同,你就可以这样玩,代码示例如下:

<!-- wxml -->
<view class="font">
<view class="font small">
<view class="font small blue">

<!-- wxss -->
.font{ text-align: center; }
.font.small{ text-size: 18rpx; } /* 小号字体 */
.font.big{ text-size: 24rpx; }  /* 大号字体 */
.font.small.blue{ text-color: blue; }    /* 蓝色小号字体 */

<!-- 写了多个,如果有重复属性定义,那么后面的会覆盖前面的! -->

关于选择器更多内容可移步至:www.w3school.com.cn/cssref/css_…


0x4、文档流

文档内元素的流动方向,内联元素从左往右,块级元素从上往下

简单点说:元素在页面出现的先后顺序

可能有些模糊,举个例子

<view style="background-color: #FFBBFF; height: 96rpx; line-height: 96rpx; text-align:center">块元素①</view>
<text style="background-color: #CAFF70; ">行内元素①</text>
<text style="background-color: #EED8AE; ">行内元素②</text>
<text style="background-color: #FFA500; ">行内元素③</text>
<view style="background-color: #F08080; height: 96rpx; line-height: 96rpx; text-align:center">块元素②</view>
<view style="background-color: #EEEE00; height: 96rpx; line-height: 96rpx; text-align:center">块元素③</view>

运行结果如下

按照:内联元素从左往右,块级元素从上往下(独占一行),这样的规则就是「正常文档流」,如果我们通过一些手段,使得元素不按照这个规则进行排布,就叫「脱离文档流」。比如为行内元素②设置一个向右的浮动:

<text style="background-color: #EED8AE; float:right">行内元素②</text>

就变成了这样:

行内元素②没有跟在①后,而③也没有跟在②后,这就是 脱离文档流


0x5、块级元素(block)与行内(inline)元素

块级元素

  • 独占一行,且宽度会占满父元素宽度,即容器的100%;
  • 可设置width和height,不过即使设置了width还是会独占一行
  • 可设置margin和padding;
  • 可容纳内联元素和其他块元素;
  • 比如:<view>标签

行内(内联)元素

  • 不独占一行,相邻行内元素可以排在同一行;
  • 宽高为文字或图片的宽高不可变,即设置width/height无效
  • 设置margin和padding 水平方向有效垂直方向无效
  • 只能容纳文本或者其他内联元素;
  • 比如:<text>标签

可以通过 display 属性来完成行内元素和块级元素的切换,有三个可选值:

  • block:设置为块元素。
  • inline:设置为行内元素。
  • inline-block行内块元素,让元素具有块级元素和行内元素的特性,即能
    设置宽高,margin和padding生效,还可以和其他行内元素并排。

举个例子

<!-- test.wxml -->
<view class="container">
  <view class="block-1">块元素-1</view>
  <view class="block-2">块元素-2</view>
  <view class="block-3">块元素-3</view>
  <view class="block-3">块元素-4</view>
  <text class="inline-1">行内元素-1</text>
  <text class="inline-2">行内元素-2</text>
  <text class="inline-3">行内元素-3</text>
  <view>
    <view class="display-inline">行内块元素-1</view>
    <view class="display-inline">行内块元素-2</view>
  </view>
  <view>
    <text class="display-block">行内块元素-3</text>
    <text class="display-block">行内块元素-4</text>
  </view>
  <view>
    <view class="display-inline-block">行内块元素-5</view>
    <view class="display-inline-block">行内块元素-6</view>
  </view>
</view>
/* test.wxss */
/* 块元素 */
.block-1{
  background: red
}
/* 块元素可以直接设置margin和padding */
.block-2 {
  background: greenyellow;
  margin-right50rpx;
  margin-top50rpx;
  padding-bottom25rpx;
  padding-left25rpx;
}

/* 块元素设置宽高,但是依旧是占一行 */
.block-3 {
  background: paleturquoise;
  height96rpx;
  width200rpx;
}

/* 行内元素 */
.inline-1 {
  background: red
}

/* 行内元素设置margin和padding,只有水平方向生效 */
.inline-2 {
  background: greenyellow;
  margin-right50rpx;
  margin-top50rpx;
  padding-bottom25rpx;
  padding-left25rpx;
}

/* 行内元素设置宽高不生效 */
.inline-3 {
  background: paleturquoise;
  height96rpx;
  width200rpx;
}

/* 块元素转换为行内元素 */
.display-inline {
  display: inline;
  background: orange;
  margin-right50rpx;
  padding-bottom25rpx;
  padding-left25rpx;
}

/* 行内元素转换为块元素 */
.display-block {
  display: block;
  background: pink;
  margin-right50rpx;
  padding-bottom25rpx;
  padding-left25rpx;
  margin-top40rpx;
  height96rpx;
  width200rpx;
}

/* 行内块元素,同时拥有块级元素和行内元素的特性 */
.display-inline-block {
  display: inline-block;
  width300rpx;
  height100rpx;
  background: gold;
  margin-left50rpx;
  margin-top20rpx;
}

运行结果如下


0x6、盒子模型

元素被描绘成「矩形盒子」,这些盒子通过一个模型来描绘它的占用空间,即「盒子模型」。

如图,盒子模型通过下述四个边界来描述:

  • Margin(外边距)—— 边框外的区域,外边距是透明的。
  • Border(边框)—— 围绕在内边距和内容外的边框。
  • Padding(内边距)—— 内容周围的区域,内边距是透明的。
  • Content(内容)—— 盒子的内容,显示文本和图像。

暂且把这个大盒子称为「元素框」,设置width和height指的是内容部分宽高设置内外边距和边框不会影响内容区域的尺寸,但是会增加元素框的总尺寸。举个例子,你定义了一个48rpx48rpx的view,但是如果你还设置了margin或padding,那么这个元素的元素框尺寸就不止48rpx48rpx了!


① box-sizing属性

如果你想设置「元素框」的宽高固定,不会因为设置了边距和边框而改变宽高,可以使用「box-sizing」来实现,该属性有下述两个可选值:

  • content-box:宽高仅是内容宽高,加上padding和border,模型宽高会变大.
  • border-box以border为边界,宽高是包括边框和内边距的,设置padding模型宽高也不会变。

使用代码示例如下

<!-- test.wxml -->
<view class="view-wrapper">
  <view class="view-1">元素1</view>
  <view class="view-2">元素2</view>
</view>
/* test.wxss */
page {
  background: gray;
}

view {
  text-align: center;
  width240rpx;
  height240rpx;
  line-height240rpx;
  border10rpx solid white;
}

.view-wrapper {
  width75%;
  background: gold;
  padding50rpx;
  overflow: hidden;
  border: none;
}

.view-1 {
  background: greenyellow;
  box-sizing: content-box;
  float: left;
}

.view-2 {
  background: blueviolet;
  box-sizing: border-box;
  float: right;
}

运行结果如下


② 外边距合并问题

当两个或更多垂直外边距相遇时,它们将形成一个外边距,合并后的外间距高度等于两个元素中外边距高度中的较大者

单看概念有点含糊,写个简单的例子来帮助理解(相邻元素):

<!-- test.wxml -->
<view class="container">
  <view class="view-1">元素1</view>
  <view class="view-2">元素2</view>
</view>

接着设置两个样式

.view-1 { background: gold; }
.view-2 { background: red; }

接着按照下述步骤修改样式:

  • ① view-1设置:margin-bottom: 50rpx
  • ② 注释掉view-1的样式,view-2设置:margin-top: 10rpx
  • ③ 去掉view-1的注释。

每一步的结果如下:

如图,两个元素最后的边距是50rpx,而不是50rpx + 10rpx = 60rpx
接着我们再来试试 负值 的情况

.view-1 { background: gold; margin-bottom: -10rpx}
.view-2 { background: red; margin-top30rpx}

运行结果如下

不难发现此时的外边距是20rpx,再试试负数比整数大的情况:

.view-1 { background: gold; margin-bottom10rpx}
.view-2 { background: red; margin-top: -20rpx}

同样不难发现此时的外边距是-10rpx,再试试两个都是负数的情况:

.view-1 { background: gold; margin-bottom: -10rpx}
.view-2 { background: red; margin-top: -20rpx}

此时的外边距是-20rpx,分析计算下规律:

  • 一正一负,先求绝对值差(绝对值大-绝对值小),再设置正负;
  • 同正同负:去绝对值大的那个,在设置正负。

如果不想面对外边距合并问题,有下述几种规避方法:

  • ① 下面的元素设置绝对定位:position:absolute;
  • ② 下面的元素设置下浮动:float:left;
  • ③ 任意一个盒子设置为为行内块元素:dispaly:inline-block

除了上面这种「相邻元素」会出现外边距合并问题外「父子元素」也可能会,
没有内边距和边框隔开。写个简单的测试例子体验下:

<view class="view-1">
  <view class="view-2">元素</view>
</view>

设置两个样式,灰色背景方便对比,设置一个左边的间距方便看。

page { background: gray; }
.view-1 { background: gold; }
.view-2 { background: red; margin-left50rpx;}

接着按照下述步骤修改样式:

  • ① view-2设置:margin-top:20rpx
  • ② 注释掉view-2,view-1设置:margin-top: 50rpx
  • ③ 去掉view-2的注释。

每一步的结果如下:

有下述几种方法可以规避父子元素外边距合并问题:

  • ① 父元素设置内边距:padding-top:1rpx
  • ② 父元素设置:overflow: hidden;
  • ③ 父元素设置边框:border:1rpx solid transparent;

关于外边距合并就说那么多吧,知道怎么规避就好,具体原因涉及到BFC(Block Formatting Context,块级格式化上下文),目前还不知道具体是啥,后面研究了再另外开一片介绍吧。


0x7、定位

让元素脱离文档流的办法是:定位,浮动或者多列布局,这里先讲解一波定位。
通过一个例子来帮助理解,先定义一个没有使用定位的页面。

<!-- test.wxml -->
<view class="view-wrapper">
  <view class="view-1">元素1</view>
  <view class="view-2">元素2</view>
  <view class="view-3">元素3</view>
  <view class="view-4">元素4</view>
</view>
/* test.wxss */
view {
  display: inline-block;
  padding10px
}
.view-wrapper { background: gold; }
.view-1 { background: greenyellow; }
.view-2 { background: blueviolet; }
.view-3 { background: orange; }
.view-4 { background: pink; }

运行结果如下


① 相对定位

相对于它在「文档流中的位置的起始点」进行移动,通过例子来体验下,这里我们为元素2添加下述样式:

position: relative;
left: 50rpx;
top: 50rpx;

运行结果如下

可以看到元素2从起始点开始,左边和上面都偏移50rpx,此处有个细节:偏移前的空间依旧存在!另外,另外注意 起始点 这个字眼,元素是基于起始点进行偏移的,比如为外层元素设置一个margin-left: 50rpx; 运行后的效果如下:


② 绝对定位

完全从文档流中抽离出来,可放到页面的任何位置。把上面设置的margin-left:50rpx删掉,接着把relative; 改为 absolute;运行效果如下:

可以看到,偏移前的空间已被删除!绝对布局是这样的定位的:

相对于它的父元素来定位」,如果父元素没有设置定位,就找父元素的父元素,依次往上,直至遇到设置了定位的父元素未知,如果没找到,就会相对于文档 body进行定位。所以这里是基于body进行定位的,我们可以试下为外层的view设置position: relative,接着运行看下效果:

购物车那种数字小红点一般就是用绝对定位实现的。另外还可以通过 z-index 属性来控制重叠排列顺序,值大的在上面。改下样式:

/* index.wxss */
.view-1 {
  background: greenyellow;
  position: absolute;
  left0rpx;
}
.view-2 {
  background: blueviolet;
  position: absolute;
  left108rpx;
  top20rpx;
}
.view-3 {
  background: orange;
  position: absolute;
  top100rpx;
  left20rpx
}
.view-4 {
  background: pink;
  position: absolute;
  left100rpx;
  top80rpx;
}

运行结果如下

加入index-z属性,控制重叠排列顺序:

/* index.wxss */
.view-1 {
  background: greenyellow;
  position: absolute;
  left0rpx;
  z-index50;
}
.view-2 {
  background: blueviolet;
  position: absolute;
  left108rpx;
  top20rpx;
  z-index30;
}
.view-3 {
  background: orange;
  position: absolute;
  top100rpx;
  left20rpx;
  z-index20;
}
.view-4 {
  background: pink;
  position: absolute;
  left100rpx;
  top80rpx;
  z-index10;
}

运行结果如下


③ 固定定位

fixed:和absolute类似,超出屏幕的时候也是固定,参考的是窗口,常用于需要悬浮固定的场景。比如商品详情页,有个一直固定在底部的购买按钮,页面内容可以正常滚动;还有基于窗口的悬浮框等。


0x8、浮动与清除浮动

使元素脱离文档流,按照指定方向(左或右)移动直到外边缘碰到包含框或另一个浮动框的边框为止。浮动前竖向排列,浮动后横向排列;float属性,可选值left左,right右。写个例子体验下,复用上面的wxml,然后设置新的样式:

/* test.wxss */
view > view {
  line-height100rpx;
  width140rpx;
  text-align: center;
}

.view-1 {
  background: greenyellow;
}

.view-2 {
  background: blueviolet;
}

.view-3 {
  background: orange;
}

.view-4 {
  background: pink;
}

运行效果如下

接着为元素1设置一个向右的浮动 float:right; 运行结果如下:

如图,元素1脱离了文档流(所占空间被删除),然后浮动到右侧了,如果想调整元素1的位置,可以设置margin,比如这里设置margin-right:20rpx;

接着我们如果为元素2也设置一个向右的浮动:

按顺序排到了右侧,之所以没有像元素1一样贴着右边而是在元素1的左侧,因为碰到元素1浮动框了。接着为元素4页设置一个右浮动:

另外有一种情形要注意一下,把样式文件修改为:

/**index.wxss**/

view > view {
  line-height100rpx;
  width240rpx;
  float: left;
  text-align: center;
}

.view-1 {
  background: greenyellow;
  height140rpx;
}

.view-2 {
  background: blueviolet;
}

.view-3 {
  background: orange;
}

.view-4 {
  background: pink;
}

包含框太窄,无法容纳水平排列的三个浮动元素,那么其它浮动块向下移动,直到有足够的空间。如果浮动元素的高度不同,那么当它们向下移动时可能被其它浮动元素“卡住”.

接着说下「清除浮动」,示例代码如下:

<!-- test.wxml -->
<view class="view-wrapper">
  <view class="view-1">元素1</view>
  <view class="view-2">元素2</view>
</view>
/* test.wxss */
page {
  background: gray;
}

.view-wrapper {
  width75%;
  background: gold;
  padding10rpx;
}

view > view {
  width240rpx;
  text-align: center;
}

.view-1 {
  background: greenyellow;
}

.view-2 {
  background: blueviolet;
}

.view-3 {
  background: orange;
}

.view-4 {
  background: pink;
}

运行结果如下

接着为两个元素分别设置左和右的浮动,运行结果如下:

卧槽,怎么就这样了?浮动带来的影响,可以为通过设置属性overflow: hidden; 来清除浮动。

除此之外还可以添加一个组件,然后设置clear:both实现相同的效果。

<view style="clear:both"/>

还有一种玩法:通过伪元素:after直接添加

.view-2:after {
  content"";
  display: block;
  clear: both;
}

当然,你也可以直接写死容器元素的高度~


0x9、多列布局multi-column

CSS3新增了一个多栏布局,用来实现「文本多列」和「瀑布流」非常方便,就顺带讲下吧~

相关属性如下

  • column-rule-style:列与列间的边框样式;
  • column-rule-width:两列的边框厚度;
  • column-rule-color:两列的边框颜色;
  • column-rule:上述所有属性的简写,示例: column-rule: 1px solid lightblue;
  • column-count:创建多列,指定需要分割的列数;
  • column-width:列的宽度;
  • columns:column-width 和 column-count 的简写。
  • column-gap:列与列间的间隙;
  • column-span:是否跨多栏显示;
  • column-fill:指定如何填充列;

文本多列的代码示例如下

<!-- test.wxml -->
<view class="view-wrapper">
  <view class="view-1">大家好,我是练习时长两年半的个人练习生菜虚鲲,我喜欢唱,跳,rap,篮球,Music!</view>
</view>
/* test.wxss */
.view-1 {
  columns:auto 5;
  column-rule5rpx solid lightblue;
}

运行结果如下

实现一个简易图片瀑布流示例如下

//test.js,新增一堆图片URL
Page({
  data: {
    pics: [
      "http://img4.imgtn.bdimg.com/it/u=529905932,1803087578&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=823139735,3514716232&fm=26&gp=0.jpg",
      "http://img4.imgtn.bdimg.com/it/u=529905932,1803087578&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=2958310391,871610286&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=2958310391,871610286&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=2958310391,871610286&fm=26&gp=0.jpg",
      "http://img2.imgtn.bdimg.com/it/u=3924656228,1474918552&fm=26&gp=0.jpg",
      "http://img4.imgtn.bdimg.com/it/u=529905932,1803087578&fm=26&gp=0.jpg",
      "http://img2.imgtn.bdimg.com/it/u=3924656228,1474918552&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=823139735,3514716232&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=2958310391,871610286&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=2958310391,871610286&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=823139735,3514716232&fm=26&gp=0.jpg",
      "http://img2.imgtn.bdimg.com/it/u=3924656228,1474918552&fm=26&gp=0.jpg",
      "http://img5.imgtn.bdimg.com/it/u=823139735,3514716232&fm=26&gp=0.jpg",
      "http://img4.imgtn.bdimg.com/it/u=529905932,1803087578&fm=26&gp=0.jpg",
      "http://img2.imgtn.bdimg.com/it/u=3924656228,1474918552&fm=26&gp=0.jpg",
    ]
  },
})
<!-- test.wxml,利用wx:for生成控件 -->
<view class="content">
  <block wx:for="{{pics}}">
    <image src="{{item}}" mode="widthFix"></image>
  </block>
</view>
/* test.wxss */
page {
  background: gray;
}

.content {
  columns: auto 3;
  width100%;
  column-gap5rpx;
}

image {
  width100%;
  display: block;
  box-sizing: border-box;
  padding5rpx;
}

运行结果如下

瀑布流是实现了,但是左下角的蕾姆酱被切成两半了,如果不想切断,可以为子元素设置「break-inside」属性来防止多列布局,分页媒体和多区域上下文中的意外中断。直接在image的样式里添加:

break-inside: avoid;

运行后结果如下


0x10、flex弹性布局

学习完前面的内容,我们可以通过display,position,float来布局,但是灵活性较差。2009年,w3c提出了一种新的布局方案:flex弹性布局,可以简便、完整、响应式地实现多种页面布局。任何元素都可以开启弹性布局,采用Flex布局的元素,称为「Flex容器(flex container)」,它里面所有的子元素会自动成为容器成员,称为「Flex 项目(flex item)」。

留意下上面的「主轴」和「侧轴」,其实就是「水平」和「垂直」两个方向。
Flex的属性分为两个部分:「容器属性」和「项目属性」,具体如下图所示:

因为属性较多,限于偏于,也不一一展示具体效果了,Runoob上有对应的效果展示,读者请自行移步至:
www.runoob.com/cssref/css3…,查看学习:

最后再提下和flex有关的两点:

第一点

设置flex布局后,子元素的float,clear和vertical属性将失效!

第二点

行内元素也可以使用Flex布局,设置display:inline-flex;即可。


0x0、布局实战:写个抠腚优鲜的首页

Tips:因内容太多,实战部分拆分到另一篇中juejin.cn/post/684490…


小结

相信读者学完本节,基本可以应付日常小程序页面的堆砌了。这种实操性比较强的东西,切忌死记,建议自己找些小程序仿写下,熟能生巧,别说没有设计稿,没有图片没有尺寸,上节学的反编译技能呢???

笔者不是专业前端,以上内容都是现学现卖,如有纰漏或建议,欢迎评论区指出,谢谢~
源码整理下再丢Gayhub,后面再发个地址哈~(另外,蹲个深圳3年半的Android坑)


参考文献


如果本文对你有所帮助,欢迎
留言,点赞,转发
素质三连,谢谢😘~