Можно ли скрыть / удалить границы внутри пересеченной области нескольких элементов? - PullRequest
4 голосов
/ 14 февраля 2020

Когда два или более div пересекаются, они просто перекрываются, и их границы видны:

.circle {
  position: absolute;
  width: 100px;
  height: 100px;
  border-radius: 50%;
  border: 1px solid black;
}

#two {
  left: 50px;
}

#three {
  left: 100px;
}
<div >
  <div class="circle" id="one"></div>
  <div class="circle" id="two"></div>
  <div class="circle" id="three"></div>
</div>

Вопрос заключается в том, возможно ли скрыть те границы, которые находятся внутри пересекаемой области, чтобы было похоже, что есть только одна большая форма. Если взять приведенный выше пример, результат должен выглядеть следующим образом:

enter image description here

Ответы [ 3 ]

4 голосов
/ 14 февраля 2020

Вы можете попробовать использовать mask и немного изменить код для лучшего контроля. Хитрость заключается в использовании нескольких масок, где каждая из них будет круговым градиентом, который будет отображать только границу, и каждый градиент будет перекрывать каждый элемент круга. Вы можете контролировать перекрытие с помощью поля на центральном элементе:

.circle {
  width: 100px;
  height: 100px;
  border-radius: 50%;
  border: 2px solid black;
  transition:0.5s;
}

.box {
  display:inline-flex;
  -webkit-mask:
     radial-gradient(50px at 52px              50%,transparent 99%,#fff 100%),
     radial-gradient(50px at 50%               50%,transparent 99%,#fff 100%),
     radial-gradient(50px at calc(100% - 52px) 50%,transparent 99%,#fff 100%);
  mask:
     radial-gradient(50px at 52px              50%,transparent 99%,#fff 100%),
     radial-gradient(50px at 50%               50%,transparent 99%,#fff 100%),
     radial-gradient(50px at calc(100% - 52px) 50%,transparent 99%,#fff 100%);
  -webkit-mask-composite: source-in;
  mask-composite: intersect;
}

body {
  background:linear-gradient(to right,pink,yellow);
}

/* You can also have animation*/
.box:hover .circle{
   margin:0!important;
}
<div class="box">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -50px;"></div>
  <div class="circle"></div>
</div>
<br>
<div class="box">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -30px;"></div>
  <div class="circle"></div>
</div>
<br>
<div class="box">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -70px;"></div>
  <div class="circle"></div>
</div>
<br>
<div class="box">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -10px;"></div>
  <div class="circle"></div>
</div>

CSS hide intersection border

И с CSS переменными для лучшего контроля:

.circle {
  width: calc(2*var(--r));
  height: calc(2*var(--r));
  border-radius: 50%;
  border: var(--b) solid black;
}

.box {
  --r:50px; /* radius of circles*/
  --b:2px;  /* border length */
  --g:transparent 99%,#fff 100%;
  
  display:inline-flex;
  -webkit-mask:
     radial-gradient(var(--r) at calc(var(--r) + var(--b))        50%,var(--g)),
     radial-gradient(var(--r) at 50%                              50%,var(--g)),
     radial-gradient(var(--r) at calc(100% - var(--r) - var(--b)) 50%,var(--g));
  mask:
     radial-gradient(var(--r) at calc(var(--r) + var(--b))        50%,var(--g)),
     radial-gradient(var(--r) at 50%                              50%,var(--g)),
     radial-gradient(var(--r) at calc(100% - var(--r) - var(--b)) 50%,var(--g));
  -webkit-mask-composite: source-in;
  mask-composite: intersect;
}

body {
  background:linear-gradient(to right,pink,yellow);
}
<div class="box">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -50px;"></div>
  <div class="circle"></div>
</div>
<br>
<div class="box" style="--r:40px;--b:5px;">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -30px;"></div>
  <div class="circle"></div>
</div>
<br>
<div class="box" style="--r:100px;--b:20px;">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -70px;"></div>
  <div class="circle"></div>
</div>
<br>
<div class="box" style="--r:80px;--b:5px;">
  <div class="circle"></div>
  <div class="circle" style="margin:0 -10px;"></div>
  <div class="circle"></div>
</div>

CSS remove intersection area

2 голосов
/ 14 февраля 2020

В соответствии с вашим первым запросом невозможно сделать границу пересечения невидимой, используя CSS. Однако, если вы хотите достичь вышеупомянутого дизайна, вы можете использовать трюк с псевдоэлементом для достижения этой цели. Вы можете создать псевдоэлемент для идентификатора "#two" и сделать его позицией абсолютной относительно высоты и ширины центра div. Вы должны сделать немного корректировки наверняка. Я добавил фрагмент для вас. Пожалуйста, попробуйте.

.circle {
            position: absolute;
            width: 100px;
            height: 100px;
            border-radius: 50%;
            border: 1px solid black;
          }

          #two {
            left: 50px;
            background: #fff;
          }

          #two:after {
            content: "";
            background: #fff;
            width: 100%;
            height: 88px;
            top: 6px;
            left: -2px;
            position: absolute;
            z-index: 9;
            -ms-transform: rotate(20deg);
            transform: rotate(.2deg);
          }

          #three {
            left: 100px;
            background: #fff;
          }
<div >
  <div class="circle" id="one"></div>
  <div class="circle" id="two"></div>
  <div class="circle" id="three"></div>
</div>
1 голос
/ 14 февраля 2020

другая возможность ie - mix-blend-mode, если доступно:

 /* === HERE ==== comment where it matters , the rest is only styling */
div {
  width: 20vmax;
  height: 20vmax;
  border: solid;
  background: white;/* === HERE ====*/
  border-radius: 50%;
  margin: auto;
  position: relative;
  font-size:4vmax;
  display:flex;
  align-items:center;
  justify-content:center;
  box-shadow:0 0 10px, inset 0 0 2px;
  animation:shift 4s infinite ease-in-out alternate;
}
div::before,
div::after {
  content: "";
  position: absolute;
  height: inherit;
  width: inherit;
  background: inherit;
  border: inherit;
  border-radius: inherit;
  box-shadow:inherit;
  mix-blend-mode:screen;/* === HERE ====*/
  animation:shift 2s infinite ease-in-out alternate;
}
div::before {
  left:-50%;
}
div::after {
  left:50%;
  animation-delay:-1s;
}
p {z-index:1;}
@keyframes shift {
25% {transform:translate(5%,-5%) scale(1.2);}
50% {transform:translate(-5%,5%) scale(0.9);}
}
html {display:flex;min-height:100vh;}
body {margin:auto;}
<div><p>Hi, Cloudy</p></div>

демо для развлечения

...