I have a disc whose size can change, and some icons arranged around that disc. The icons should always be on the border of the disc, and the intervals between each icon should always stay the same.
Can this be done in pure css without having to compute each icon's position whenever the disc grows or shrinks?
Expected result:
.container:nth-child(1)
{
position: absolute;
top: 20px;
left: 30px;
height: 280px;
width: 280px;
}
.container:nth-child(2)
{
position: absolute;
top: 20px;
right: 30px;
height: 200px;
width: 200px;
}
.container > *
{
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
.circle
{
height: 90%;
width: 90%;
border-radius: 50%;
border: 1px solid blue;
z-index: 20;
}
.icons
{
height: 100%;
width: 100%;
border: 1px dashed gray;
box-sizing: border-box;
z-index: 10;
}
.icons > *
{
position: absolute;
top: 50%;
left: 50%;
height: 20px;
width: 20px;
margin-top: -10px;
margin-left: -10px;
border: 1px solid red;
}
.container:nth-child(1) span:nth-child(1)
{
transform: rotate(230deg) translate(150px) rotate(-230deg);
}
.container:nth-child(1) span:nth-child(2)
{
transform: rotate(217deg) translate(150px) rotate(-217deg);
}
.container:nth-child(1) span:nth-child(3)
{
transform: rotate(204deg) translate(150px) rotate(-204deg);
}
.container:nth-child(1) span:nth-child(4)
{
transform: rotate(191deg) translate(150px) rotate(-191deg);
}
.container:nth-child(2) span:nth-child(1)
{
transform: rotate(230deg) translate(110px) rotate(-230deg);
}
.container:nth-child(2) span:nth-child(2)
{
transform: rotate(212deg) translate(110px) rotate(-212deg);
}
.container:nth-child(2) span:nth-child(3)
{
transform: rotate(194deg) translate(110px) rotate(-194deg);
}
.container:nth-child(2) span:nth-child(4)
{
transform: rotate(176deg) translate(110px) rotate(-176deg);
}
<div class="container">
<div class="circle"></div>
<div class="icons">
<span>A</span>
<span>B</span>
<span>C</span>
<span>D</span>
</div>
</div>
<div class="container">
<div class="circle"></div>
<div class="icons">
<span>A</span>
<span>B</span>
<span>C</span>
<span>D</span>
</div>
</div>
There is a way to do it programmatically, but only with CSS3. What you have to do is have an element inside it that takes the full width and can rotate, and then counterrotate the inner containers of those rotating elements.
So you would have to define the circles by using
:nth-child. In order to achieve the correct effect and not apply a style twice, we will have to count down from our last element in order to only attract elements at a certain position. This is because:nth-child(2n)applies to:nth-child(4n)as well, which might create overlapping styles. Skip to the snippet if this seems a bit too complicated - it's actually quite simple.So your basic HTML would be:
The first element has to have a position enabled. The second element needs to overlap with all the other secondary elements, so it needs a position of absolute, and the third element, well, that's up to you. It's just there to counter rotate it again.
Heres an implementation:
There is a way to automate this is SASS as well and it looks something like this:
You can call it by doing the following:
And you can optionally include which elements you want to use as the children. Don't forget they all need some absolute positioning for this to work. Don't forget to add any
prefixesyou need (I added them to the snippet because I am using Safari)