如何使用CSS将圆形分割成不同颜色的部分

44

我希望能够绘制一个带有不同颜色部分的圆,我想使覆盖该部分的量能够以10%的增量从0%100%递增。

谷歌上的任何示例都是扇形而不是圆弧。

Segments

目前为止,这是我能想到的最好的方法:

div.outerClass {
    position: absolute;
    left: 10px;
    top: 10px;
    height: 2.5px;
    overflow: hidden;
    -ms-transform: rotate(270deg); /* IE 9 */
    -webkit-transform: rotate(270deg); /* Chrome, Safari, Opera */
    transform: rotate(270deg);
}

div.innerClass {
    width: 10px;
    height: 10px;
    border: 5px solid green;
    border-radius: 36px;
}
<div class="outerClass">
    <div class="innerClass"></div>
</div>

我可以完成0%、50%和100%的任务。

4个回答

51

您可以使用linear-gradient来完成此操作。

.circle{
  position:absolute;
  width:80px;
  height:80px;
  border-radius:50%;
  background: linear-gradient(
    to right,
    yellow  0%, yellow 10%,
    orange 10%, orange 20%,
    yellow 20%, yellow 30%,
    orange 30%, orange 40%,
    yellow 40%, yellow 50%,
    orange 50%, orange 60%,
    yellow 60%, yellow 70%,
    orange 70%, orange 80%,
    yellow 80%, yellow 90%,
    orange 90%, orange 100%
  );
}
<div class="circle"></div>

否则您可以将10个子元素放在overflow:hidden的圆形父元素中:

.circle{
  position:absolute;
  width:80px;
  height:80px;
  border-radius:50%;
  overflow:hidden;
}
.circle > span{
  width:10%;
  height:100%;
  float:left;
}

.circle > span:nth-child(1){ background: yellow;}
.circle > span:nth-child(2){ background: orange;}
.circle > span:nth-child(3){ background: blue;}
.circle > span:nth-child(4){ background: green;}
.circle > span:nth-child(5){ background: fuchsia;}
.circle > span:nth-child(6){ background: orange;}
.circle > span:nth-child(7){ background: gold;}
.circle > span:nth-child(8){ background: tan;}
.circle > span:nth-child(9){ background: navy;}
.circle > span:nth-child(10){background: brown;}
<div class="circle">
  <span></span><span></span><span></span><span></span><span></span>
  <span></span><span></span><span></span><span></span><span></span>
</div>


7
@user2871826 坦率地说,我看不出Sergey的答案怎么更简单。随你喜欢 :) 不客气。 - Roko C. Buljan
长度更短,使用它实现系统会更容易。但是在简单性方面并没有太大的区别。 - Greg
9
与最多11个元素相比,这种渐变只使用一个元素……对我来说似乎更简单了……而且它也可以正确地容纳内容。 - Paulie_D
@Cornstalks https://dev59.com/7Ww15IYBdhLWcg3wntKh - Roko C. Buljan
ن½؟用linear-gradientن»£و›؟-webkit-linear-gradient,è؟™و ·ه…¶ن»–وµڈ览ه™¨çڑ„用وˆ·ن¹ں能看هˆ°و¼”ç¤؛م€‚ - Salman A
显示剩余3条评论

45

跨浏览器解决方案:

JSFiddle

.circle {
    border-radius: 50%;
    background: gray;
    width: 300px;
    height: 300px;
    overflow: hidden;
}
.segment {
    float: left;
    width: 10%;
    height: 100%;
}
    .segment_1 {
        background: red;
    }
    .segment_2 {
        background: green;
    }
    .segment_3 {
        background: yellow;
    }
    .segment_4 {
        background: blue;
    }
<div class="circle">
    <div class="segment segment_1"></div>
    <div class="segment segment_2"></div>
    <div class="segment segment_3"></div>
    <div class="segment segment_4"></div>
</div>


4
@grgarside 因为它只改变了格式样式,我不喜欢它。如果 SO 有自己的帖子/代码样式指南,请给我链接。 - sergdenisov
2
@grgarside 抱歉,我没有注意到堆栈片段。已回滚并修复了格式。 - sergdenisov
1
@grgarside:说句公道话,他也没必要改变格式样式来使其在堆栈片段中运行。即使他使用堆栈片段编辑器生成片段,他也可以将代码原封不动地复制,它也会正常工作。完全没有理由需要重新格式化它。 - BoltClock
我将代码转换为一个stacksnippet,并在此过程中点击了整理按钮。顺便说一下,缩进对我来说看起来很奇怪。我不明白为什么你会缩进.segment_...类,但不缩进.segment本身。 - Salman A
2
@SalmanA 我喜欢这样格式化它。http://getbem.com/introduction/ — .segment 是块,.segment_... 是修饰符。 - sergdenisov
@Falmarri 如果这对您非常重要,我可以详细解释。 - sergdenisov

15

方框阴影

另一种方法是使用一个元素和方框阴影。

  • 主要元素是圆形(border-radius: 50%;),长宽比为1:1。

  • 伪元素的位置是 left: -100%;,即在主要元素的左侧。

  • 10个方框阴影被应用到伪元素上,每个阴影颜色和横坐标都不同。我将横坐标定为30px,因为30px是300px的10%...

  • 选择了宽度的10%是因为需要10条条纹。

div {
  height: 300px;
  width: 300px;
  border: 1px solid black;
  position: relative;
  border-radius: 50%;
  overflow: hidden;
}
div:before {
  position: absolute;
  content: '';
  height: inherit;
  width: inherit;
  left: -100%;
  background: red;
  box-shadow: 
    30px 0 0 chocolate,
    60px 0 0 hotpink,
    90px 0 0 indigo,
    120px 0 0 orangered,
    150px 0 0 gold,
    180px 0 0 deepskyblue,
    210px 0 0 springgreen,
    240px 0 0 darkslategray,
    270px 0 0 gold,
    300px 0 0 navy;
}
<div></div>


1
我真的很惊讶,没有人使用盒子阴影来回答这个问题!我以为已经有人发布了它。你刚看到这个问题吗?我也开始制作一个小样例:https://jsfiddle.net/nqys0fyo/ :) - Max Payne

13

另一种方法是使用SVG。这些线段使用<rect />元素制成,并使用<clipPath/>元素剪切为圆形:

svg{width:40%;display:block;margin:0 auto;}
use:hover{fill:#000;}
<svg viewBox="0 0 10 10">
  <defs>
    <clipPath id="circle">
      <circle cx="5" cy="5" r="5" />
    </clipPath>
    <rect id="seg" y="0" width="1" height="10" />
  </defs>  
  <g clip-path="url(#circle)">
    <use xlink:href="#seg" x="0" fill="pink"/>
    <use xlink:href="#seg" x="1" fill="green" />
    <use xlink:href="#seg" x="2" fill="orange" />
    <use xlink:href="#seg" x="3" fill="teal" />
    <use xlink:href="#seg" x="4" fill="tomato"/>
    <use xlink:href="#seg" x="5" fill="gold"/>
    <use xlink:href="#seg" x="6" fill="darkorange" />
    <use xlink:href="#seg" x="7" fill="pink" />
    <use xlink:href="#seg" x="8" fill="red" />
    <use xlink:href="#seg" x="9" fill="yellow" />
  </g>
</svg>


1
SVG 规则!(如果您不担心 IE8)很好的例子。我们应该真正开始/继续关注 SVG 并展示更多的 ♥。 - Roko C. Buljan
1
Raphael与VML回退将适用于IE 6.0+。 - Max Payne
1
@RokoC.Buljan 是的,尽管这种情况可以很容易地通过CSS处理,但我相信给SVG更多的♥对每个人都是一个真正的好处 :) - web-tiki
在这种情况下,SVG与已接受的答案相比没有优势。它具有相同数量的元素。 - Max Payne
@TimKrul 这取决于您需要对形状做什么。如果HTML元素的数量是选择标准,那么您的答案是最好的。 - web-tiki
@Web-tiki 我的意思是,相比已经被接受的答案(使用HTML CSS),SVG不会有任何优势。无论需要使用什么方法来处理SVG,都可以通过简单的HTML和CSS完成。例如不同颜色的悬停效果。单个元素是无法实现的。 - Max Payne

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接