CSS - 如何改变两个对象相交的背景?

CSS - How to change background of intersection of two objects?

我正在尝试复制 this animation 的样式,但我不知道如何“填充”这两个形状相交处的背景颜色。在动画中,交点是逐步的,并在正方形的边缘与圆的原点相交处停止;我可以想象使用剪贴蒙版来填充圆的那个象限。但是,是否可以更动态地做同样的事情?你能填充两个相交形状的背景吗(同时其他地方仍然有透明背景)?

.shape-interconnected {
     width: 400px;
     height: 300px;
     position: relative;
     background-color: black;
     color: white;
     margin: 1rem;
     border-radius: 4px;
}
 .shape-interconnected > .square, .shape-interconnected > .circle {
     width: 50px;
     height: 50px;
     position: absolute;
     border: 5px solid white;
     transform: translate(-50%, -50%);
}
 .shape-interconnected > .square {
     border-radius: 4px;
     top: 45%;
     left: 55%;
}
 .shape-interconnected > .circle {
     border-radius: 50%;
     top: 55%;
     left: 45%;
}
 
<div class="shape-interconnected">
  <div class="square"></div>
  <div class="circle"></div>
</div>

您可以在正方形内添加一个白色圆圈,并将其放置在与透明圆圈相同的坐标上。
设置overflow: hidden为正方形隐藏白色圆圈外面的部分:

.shape-interconnected {
  width: 400px;
  height: 300px;
  position: relative;
  background-color: black;
  color: white;
  margin: 1rem;
  border-radius: 4px;
  --animation-props: 1s alternate linear infinite;
}

.shape-interconnected>.square,
.shape-interconnected>.square:before,
.shape-interconnected>.circle {
  width: 50px;
  height: 50px;
  position: absolute;
  border: 5px solid white;
  transform: translate(-50%, -50%)
}

.shape-interconnected>.square {
  top: 35%;
  left: 65%;
  border-radius: 4px;
  overflow: hidden;
  animation: for_square var(--animation-props);
}

.shape-interconnected>.circle {
  top: 65%;
  left: 35%;
  border-radius: 50%;
  animation: for_transparent_circle var(--animation-props);
}

.shape-interconnected>.square:before {
  content: '';
  border-radius: 50%;
  background: #fff;
  top: 230%;
  left: -190%;
  animation: for_white_circle var(--animation-props);
}

@keyframes for_square {
  to {
    top: 50%;
    left: 55%;
  }
}

@keyframes for_transparent_circle {
  to {
    top: 55%;
    left: 50%;
  }
}

@keyframes for_white_circle {
  to {
    top: 80%;
    left: 10%;
  }
}
<div class="shape-interconnected">
  <div class="square"></div>
  <div class="circle"></div>
</div>

您可以使用 html 和一点 css 伪动画魔法重新创建 dribble

下面的示例适用于在根 css vars.

中定义的任何集 css 变量集 size border
:root {
  --size: 250px;
  --border: 5px;
}

我的示例中的技巧是使用百分比定位,这意味着父 .shape-interconnected 由 css var size 控制,指示所有子元素和子伪元素位置。

这里有很多css需要解释,我在css中添加了评论,看看这是否能激励你到达你需要去的地方...

这是一个fiddle...https://jsfiddle.net/joshmoto/378Lcgp0/

/* our root css vars */
:root {
  --size: 250px;
  --border: 5px;
}

BODY {
  background: black;
  min-height: 100%;
}

/* reset our box sizing on psuedo elems */
*, ::after, ::before {
    box-sizing: border-box;
}

/* our shape intersect container positioned center of window */
/* this can be positioned where ever you want */
.shape-interconnected {
  background: black;
  width: var(--size);
  height: var(--size);
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%,-50%);
  animation: shape-interconnected 2s infinite;
}

/* animate height and width equally  */
@keyframes shape-interconnected {
  0% {
    width: var(--size);
    height: var(--size);
  }
  50% {
    width: calc(var(--size) * 0.6);
    height: calc(var(--size) * 0.6);
  }
  100% {
    width: var(--size);
    height: var(--size);
  }
}

/* our square calculated at 40% of parent */
/* position and overflow hidden are key, hiding pseudo child elems */
.shape-interconnected > .square {
  width: calc(var(--size) * 0.4);
  height: calc(var(--size) * 0.4);
  background: transparent;
  position: absolute;
  overflow: hidden;
  right: 0;
  top: 0;
}

/* our square before pseudo elem emulating inner white filled circle */
/* position absolute with animation keyframes */
.shape-interconnected > .square::before {
  content: "";
  display: block;
  width: 100%;
  height: 100%;
  background: #fff;
  border-radius: 50%;
  position: absolute;
  animation: circle-interconnected 2s infinite;
}

/* start top/right 150% away, overflowing out of view */
/* 50% keyframe top/right 50% away, in view */
@keyframes circle-interconnected {
  0% {
    top: 150%;
    right: 150%;
  }
  50% {
    top: 50%;
    right: 50%;
  }
  100% {
    top: 150%;
    right: 150%;
  }
}

/* our square after pseudo elem emulating white border */
.shape-interconnected > .square::after {
  content: "";
  display: block;
  width: 100%;
  height: 100%;
  background: transparent;
  border: var(--border) solid white;
  position: relative;
}

/* our circle calculated at 40% of parent */
.shape-interconnected > .circle {
  width: calc(var(--size) * 0.4);
  height: calc(var(--size) * 0.4);
  position: absolute;
  bottom: 0;
  left: 0;
}

/* our circle after pseudo elem emulating white border */
.shape-interconnected > .circle::after {
  content: "";
  display: block;
  width: 100%;
  height: 100%;
  background: transparent;
  border: var(--border) solid white;
  border-radius: 50%;
  position: relative;
}
<div class="shape-interconnected">
  <div class="square"></div>
  <div class="circle"></div>
</div>


这是另一个使用上述相同代码但具有这些 css 根变量设置的示例...

:root {
  --size: 500px;
  --border: 2px;
}

下面的实例...

/* our root css vars */
:root {
  --size: 500px;
  --border: 2px;
}

BODY {
  background: black;
  min-height: 100%;
}

/* reset our box sizing on psuedo elems */
*, ::after, ::before {
    box-sizing: border-box;
}

/* our shape intersect container positioned center of window */
/* this can be positioned where ever you want */
.shape-interconnected {
  background: black;
  width: var(--size);
  height: var(--size);
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%,-50%);
  animation: shape-interconnected 2s infinite;
}

/* animate height and width equally  */
@keyframes shape-interconnected {
  0% {
    width: var(--size);
    height: var(--size);
  }
  50% {
    width: calc(var(--size) * 0.6);
    height: calc(var(--size) * 0.6);
  }
  100% {
    width: var(--size);
    height: var(--size);
  }
}

/* our square calculated at 40% of parent */
/* position and overflow hidden are key, hiding pseudo child elems */
.shape-interconnected > .square {
  width: calc(var(--size) * 0.4);
  height: calc(var(--size) * 0.4);
  background: transparent;
  position: absolute;
  overflow: hidden;
  right: 0;
  top: 0;
}

/* our square before pseudo elem emulating inner white filled circle */
/* position absolute with animation keyframes */
.shape-interconnected > .square::before {
  content: "";
  display: block;
  width: 100%;
  height: 100%;
  background: #fff;
  border-radius: 50%;
  position: absolute;
  animation: circle-interconnected 2s infinite;
}

/* start top/right 150% away, overflowing out of view */
/* 50% keyframe top/right 50% away, in view */
@keyframes circle-interconnected {
  0% {
    top: 150%;
    right: 150%;
  }
  50% {
    top: 50%;
    right: 50%;
  }
  100% {
    top: 150%;
    right: 150%;
  }
}

/* our square after pseudo elem emulating white border */
.shape-interconnected > .square::after {
  content: "";
  display: block;
  width: 100%;
  height: 100%;
  background: transparent;
  border: var(--border) solid white;
  position: relative;
}

/* our circle calculated at 40% of parent */
.shape-interconnected > .circle {
  width: calc(var(--size) * 0.4);
  height: calc(var(--size) * 0.4);
  position: absolute;
  bottom: 0;
  left: 0;
}

/* our circle after pseudo elem emulating white border */
.shape-interconnected > .circle::after {
  content: "";
  display: block;
  width: 100%;
  height: 100%;
  background: transparent;
  border: var(--border) solid white;
  border-radius: 50%;
  position: relative;
}
<div class="shape-interconnected">
  <div class="square"></div>
  <div class="circle"></div>
</div>