你不知道的CSS

浏览: 155 发布日期: 2017-09-05 分类: css

本文首发于我的博客

CSS的世界是神奇的。
随着各浏览器WEB标准的日趋统一,CSS在WEB世界中扮演的角色也愈发的重要。甚至于在GitHub上出现了You-Dont-Need-JavaScript这样Star近万的优秀开源项目,抛开该项目的实用性不说,项目中的众多的DEMO就已经证明了CSS的强大。
当然,这篇文章不是为了介绍这个项目,而是整理了一些实用的CSS技巧,来解决我们在实际项目开发中遇到的的问题。文章也会长期更新,总结更多的技巧。每个技巧将结合demo或者图示来说明(如果demo无法打开,请自备梯子,原因你懂得????)。也许你此刻正在发愁的一个bug可以在这里找到答案????。

~ / + 兄弟选择器来美化表单元素

css(3)中选择器众多,具体可参考CSS 选择器参考手册。不知什么原因,在很多项目中,实现诸如单选,复选等(类似)功能(包括如图标签选择器)时,为了美化其样式,往往使用JS去实现,实际上,利用label标签和css的兄弟选择器完全可以实现类似效果。其兼容性也并不差,至少兼容IE8及其以上浏览器了。

选择器解释

  1. ~ 选择器:查找某一个元素的后面的所有兄弟元素

  2. + 选择器:查找某一个元素的后面紧邻的兄弟元素

实现类某东标签选择器效果

查看demo

.tags-select {
  font-size: 0;
  >.tag-select {
    display: inline-block;
    font-size: 14px;
    margin: 5px;
    position: relative;
    font-weight: normal;
    .name {
      display: block;
      line-height: 20px;
      padding: 8px 10px;
      border: 1px solid #ccc;
      cursor: pointer;
    }
    //设置radio不可见
    input[type="radio"] {
      position: absolute;
      opacity: 0;
      z-index: -1;
      //选中
      &:checked+.name {
        border-color: #e3393c;
      }
      //禁用
      &:disabled+.name {
        background: #eee;
        color: #999;
        cursor: not-allowed;
      }
    }
  }
}
<label class="tag-select">
  <input type="radio" name="bye-type" value="1">
  <span class="name">官方标配</span>  
</label>
<label class="tag-select">
  <input type="radio" name="bye-type" value="2" checked>
  <span class="name">移动优惠购</span>  
</label>
<label class="tag-select">
  <input type="radio" name="bye-type" value="3" disabled>
  <span class="name">联通优惠购</span>  
</label>

利用label和选择器实现form元素的美化,展开来就可以写一篇博客了,因此,实现input[type="radio"], input[type="checkbox"]的美化以及switch开关控件,就不贴代码了,具体代码见我的项目mo-css

switch开关

查看demo

radio美化

查看demo

checkbox美化

查看demo

font-size:0 来清除间距

inline-block的元素之间会受空白区域的影响,也就是元素之间差不多会有一个字符的间隙。如果在同一行内有4个25%相同宽度的元素,会导致最后一个元素掉下来(如图)。你可以利用元素浮动float,或者压缩html,清除元素间的空格来解决。但最简单有效的方法还是设置父元素的font-size属性为0

*{
  box-sizing: border-box;
}
.items {
  font-size: 0;
  > .item {
    display: inline-block;
    width: 25%;
    height: 50px;
    border: 1px solid #ccc;
    text-align: center;
    line-height: 50px;
    background-color: #eee;
    font-size: 16px; //不要忘了给子元素设置字号
  }
}
<div class="items">
  <div class="item">1</div>
  <div class="item">2</div>
  <div class="item">3</div>
  <div class="item">4</div>
</div> 

overflow 來清除浮动

除了著名的clearfix清除浮动类,利用overflow属性也可以清除浮动。
overflow除了定义溢出元素内容区的内容会如何处理外,还可以做一些有用的事,如:

  • 创建块格式化上下文

  • 清除浮动

假如你的案例中没有对溢出的操作(如下拉菜单),推荐使用overflow:hidden来清除浮动。

.clearfix {
   overflow: hidden; 
}
<div class="clearfix">
  <div class="left">left</div>
  <div class="right">right</div>
</div>  

border来绘制三角形

原理

为了更清晰的展示border,将盒子的四边设为不同的颜色。

.border-arrow {
  width: 256px;
  height: 256px;
  border: 48px solid ;
  border-top-color: red;
  border-right-color : blue;
  border-bottom-color: green;
  border-left-color: orange;
}

可以看到是每个边并不是矩形,而是呈现为等腰梯形(脑洞开一下,同样我们可以使用该方法绘制梯形),这时候,如果将盒子的宽度和高度设为0,盒子将展现为如下由四个三角形组成的矩形形式:

.border-arrow {
  width: 0;
  height: 0;
  border-width: 96px;
}

现在,思路已经很清晰了,只需要将其他三个边的颜色设为透明 (transparent 或者 rgba(0, 0, 0, 0)) ,就会只保留一个三角形了。

.border-arrow {
 width: 0;
 height: 0;
 border: 72px solid ;
 border-color : transparent transparent transparent orange ;
}

延伸来绘制一个梯形

就着上面的思路,我们保留盒子宽高值,而是将其他三个边设为透明,则盒子会呈现为一个梯形:

.border-arrow {
  width: 256px;
  height: 256px;
  border: 64px solid ;
  border-color : red transparent transparent transparent ;
}

用垂直方向的padding来实现等比缩放的盒子

固定图片百分比是一个针对响应式布局很有效的方案,尤其是在移动端,可以说是一个刚性需求。简单来说,就是根据容器的宽度,按照宽高比例自动计算出容器的大小,并且让容器内的如img等子元素自适应宽高。

需求

移动端的商品列表展示,每行显示两个商品,使用懒加载技术来加载商品的缩略图,需求规定了商品必须有序整齐的排列,并且加载时要使用默认图片来占位缩略图,在加载过程中,页面的高度不能有抖动。当然,缩略图是大小是UI固定了比例的,假设比例是4:3;此时,你可能的做法是给图片容器固定高度(图片可能会变形),或者使用JS,利用屏幕的宽度和图片比例计算出图片的高度(要用到JS,要考虑屏幕旋转后宽度的变化)。

解决方案

不妨考虑考虑如下方案,本博客实验室列表页使用了该方案。

图片父容器宽度100%,父容器的高度百分比为:100*3 / 4 = 75% ; 图片absolute并且完全铺满父容器。

.image-aspect-ratio {
  width: 100%;
  position: relative;
  padding-top: 75%;
   > img {
    width: 100%;
    height: 100%;
    position: absolute;
    top: 0;
    left: 0;  
  }
}
 <figure class="image-aspect-ratio">
    <img src="http://via.placeholder.com/640x384">
 </figure> 

OK,UI只需要做一张4:3的占位图,然后利用图片懒加载技术来在页面滚动过程中加载商品图片,加载过程中页面完全不会抖动,屏幕旋转后,图片高度也随之变化,没有使用JS,一切完美解决????。

查看demo image-aspect-ratio ,可缩放浏览器查看自适应效果。

pointer-event来禁用事件

pointer-event属性更像是一个JavaScript事件,利用该属性,可以做如下的事情:

  • 阻止任何点击动作的执行

  • 使链接显示为默认光标(cursor:default)

  • 阻止触发hoveractive状态

  • 阻止JavaScript点击事件的触发

//使用该类,任何点击事件将无效
.disabled { pointer-events: none; }

max-width来防止图片撑破容器

针对内容性的文案,图片大小都是未知的,为了防止图片过大而撑破容器,可以通过设置图片的max-width:100%来处理;

img {
  display:inline-block;
  max-width: 100%;  
}

用伪类来显示打印时a标签的链接

@media print {
  a[href]:after {
    content: " (" attr(href) ") ";
  }
}

待补充条目

还有许多知识点待补充,受文章长度限制,以下或者更多内容将在新文章中补充。

  • counter来模拟/装饰有序清单

  • 未知高度容器的多种垂直居中方法

参考文档

本文首发于我的博客

返回顶部