suchen

Heim  >  Fragen und Antworten  >  Hauptteil

Eine Methode zum dynamischen Rendern kreisförmiger Sektoren ohne Verwendung von HTML5-Canvas

<p>Ich baue ein Glücksrad und muss basierend auf der Anzahl der Sektoren ein Rad oder einen Kreis erstellen und es mit dem Namen des Preises füllen. </p> <p>Ich habe den Code für einen Kreis mit einer festen Anzahl von Sektoren vervollständigt. Hier ist ein Beispiel für einen Kreis mit 6 Sektoren. </p> <p> <pre class="brush:css;toolbar:false;">.wheel_container { Position: relativ; --wheel-size: 360px; Breite: var(--wheel-size); Höhe: var(--wheel-size); Rand unten: 2,4em; } .Rad { Anzeige: Flex; rechtfertigen-Inhalt: Mitte; Position: relativ; Überlauf versteckt; Breite: 100 %; Höhe: 100 %; Randradius: 50 %; Hintergrundfarbe: Aquamarin; --segment-deg: 60deg; } .wheel div { Anzeige: Flex; rechtfertigen-Inhalt: Mitte; align-items: center; Position: absolut; Breite: calc((2 * 3.141592653589793 * (var(--wheel-size) / 2)) / 6); Höhe: 50 %; Clip-Pfad: Polygon(0 0, 50 % 100 %, 100 % 0); Transformationsursprung: unten; Schreibmodus: vertikal-rl; } .wheel div > span { Schriftstärke: 500; Schriftgröße: 1rem; Textausrichtung: Mitte; Farbe: rgba(0, 0, 0, 0,7); } .wheel div:nth-child(1) { Hintergrundfarbe: Beige; transformieren: rotieren(calc(-1 * var(--segment-deg) / 2)); } .wheel div:nth-child(2) { Hintergrundfarbe: blauviolett; transformieren: rotieren(calc(-3 * var(--segment-deg) / 2)); } .wheel div:nth-child(3) { Hintergrundfarbe: Purpur; transformieren: rotieren(calc(-5 * var(--segment-deg) / 2)); } .wheel div:nth-child(4) { Hintergrundfarbe: Orange; transformieren: rotieren(calc(-7 * var(--segment-deg) / 2)); } .wheel div:nth-child(5) { Hintergrundfarbe:violett; transformieren: rotieren(calc(-9 * var(--segment-deg) / 2)); } .wheel div:nth-child(6) { Hintergrundfarbe: gelb; transformieren: rotieren(calc(-11 * var(--segment-deg) / 2)); }</pre> <pre class="brush:html;toolbar:false;"><div class='wheel_container'> <div class='wheel'> <div><span>Apple</span></div> <div><span>Durian</span></div> <div><span>Banane</span></div> <div><span>Mango</span></div> <div><span>Erdbeere</span></div> <div><span>Jackfrucht</span></div> </div> </div></pre> </p> <p>Ich habe versucht, die Eigenschaft <code>width</code> des <code>.wheel div</code> zu bestimmen, indem ich den Umfang des Rades dividiert durch die Anzahl der Sektoren berechnet habe. Dies funktioniert jedoch nicht, da das Polygon in <code>clip-path</code> nicht gekrümmt ist, während das <code><div></code> immer noch ein Feld ist. </p> <p>Ich konnte den gewünschten Effekt von 6 Sektorkreisen erzielen, indem ich einige Pixel zur Breite von <code><div></code> hinzufügte. </p> <p> <pre class="brush:css;toolbar:false;">.wheel_container { Position: relativ; --wheel-size: 360px; Breite: var(--wheel-size); Höhe: var(--wheel-size); Rand unten: 2,4em; } .Rad { Anzeige: Flex; rechtfertigen-Inhalt: Mitte; Position: relativ; Überlauf versteckt; Breite: 100 %; Höhe: 100 %; Randradius: 50 %; Hintergrundfarbe: Aquamarin; --segment-deg: 60deg; } .wheel div { Anzeige: Flex; rechtfertigen-Inhalt: Mitte; align-items: center; Position: absolut; /* Änderung */ Breite: calc((2 * 3.141592653589793 * ((var(--wheel-size) + 37px) / 2)) / 6); Höhe: 50 %; Clip-Pfad: Polygon(0 0, 50 % 100 %, 100 % 0); Transformationsursprung: unten; Schreibmodus: vertikal-rl; } .wheel div>span { Schriftstärke: 500; Schriftgröße: 1rem; Textausrichtung: Mitte; Farbe: rgba(0, 0, 0, 0,7); } .wheel div:nth-child(1) { Hintergrundfarbe: Beige; transformieren: rotieren(calc(-1 * var(--segment-deg) / 2)); } .wheel div:nth-child(2) { Hintergrundfarbe: blauviolett; transformieren: rotieren(calc(-3 * var(--segment-deg) / 2)); } .wheel div:nth-child(3) { Hintergrundfarbe: Purpur; transformieren: rotieren(calc(-5 * var(--segment-deg) / 2)); } .wheel div:nth-child(4) { Hintergrundfarbe: Orange; transformieren: rotieren(calc(-7 * var(--segment-deg) / 2)); } .wheel div:nth-child(5) { Hintergrundfarbe:violett; transformieren: rotieren(calc(-9 * var(--segment-deg) / 2)); } .wheel div:nth-child(6) { Hintergrundfarbe: gelb; transformieren: rotieren(calc(-11 * var(--segment-deg) / 2)); }</pre> <pre class="brush:html;toolbar:false;"><div class='wheel_container'> <div class='wheel'> <div><span>Apple</span></div> <div><span>Durian</span></div> <div><span>Banane</span></div> <div><span>Mango</span></div> <div><span>Erdbeere</span></div> <div><span>Jackfrucht</span></div> </div> </div></pre> </p> <p>Der Code, der für 6 Sektoren funktioniert, funktioniert jedoch nicht für 8 Sektoren und so weiter...</p> <p>Ich denke, die Lösung könnte in den SVG-Auffüllregeln unter Verwendung von <code>clip-path</code> liegen. Allerdings reichen meine SVG-Kenntnisse nur bis zu einem gewissen Punkt und ich brauche etwas Hilfe. Auch andere Lösungen sind willkommen. </p>
P粉731861241P粉731861241448 Tage vor535

Antworte allen(1)Ich werde antworten

  • P粉460377540

    P粉4603775402023-09-03 09:02:45

    您遇到的问题是计算 .wheel div 的宽度和高度的方式不正确。如果高度是圆的半径:--radius: calc(var(--wheel-size) / 2 );,那么宽度就是 width: calc( 2 * var(--radius ) / 1.732);,其中 1.732 是 Math.sqrt(3)。这适用于一个有 6 个部分的轮子,其中三角形(用于剪切路径)是等边三角形。

    在您的示例中,宽度等于半径。这是不够的,因为 div 超出了圆形,并且您根据 div 的大小计算了剪切路径。

    为了了解发生了什么,请删除 border-radius: 50%;,并向轮子添加一个半透明的未剪切的部分(clip-path: none;)

    console.log(Math.sqrt(3))
    *{margin:0;padding:0}
    
    
    .wheel_container {
      position: relative;
      
      --wheel-size: 360px;
      width: var(--wheel-size);
      height: var(--wheel-size);
      
      margin-bottom: 2.4em;
    }
    
    .wheel {
      display: flex;
      justify-content: center;
      
      position: relative;
      overflow: hidden;
      
      width: var(--wheel-size);
      height: var(--wheel-size);
      
      border-radius: 50%;
      background-color: aquamarine;
      --segment-deg: 60deg;
    }
    
    .wheel div {
      display: flex;
      justify-content: center;
      align-items: center;
      
      position: absolute;
      
      
      --radius: calc(var(--wheel-size) / 2 );
      height: var(--radius);
      
      width: calc( 2 * var(--radius ) / 1.732);
      clip-path: polygon(0 0, 50% 100%, 100% 0);
      
      transform-origin: bottom;
      writing-mode: vertical-rl;
    }
    
    .wheel div > span {
      font-weight: 500;
      font-size: 1rem;
      text-align: center;
      color: rgba(0, 0, 0, 0.7);
    }
    
    .wheel div:nth-child(1) {
      background-color: beige;
      transform: rotate(calc(-1 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(2) {
      background-color: blueviolet;
      transform: rotate(calc(-3 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(3) {
      background-color: crimson;
      transform: rotate(calc(-5 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(4) {
      background-color: orange;
      transform: rotate(calc(-7 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(5) {
      background-color: violet;
      transform: rotate(calc(-9 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(6) {
      background-color: yellow;
      transform: rotate(calc(-11 * var(--segment-deg) / 2));
    }
    
    
    ..wheel div {transform:none!important}
    <div class='wheel_container'>
      <div class='wheel'>
        <div><span>Apple</span></div>
        <div><span>Durian</span></div>
        <div><span>Banana</span></div>
        <div><span>Mango</span></div>
        <div><span>Strawberry</span></div>
        <div><span>Jackfruit</span></div>
      </div>
    </div>

    为了进行 8 个部分的轮子,您将需要一个 --segment-deg:45 和不同的 .wheel div 的宽度。我使用的是 width: calc( 2 * var(--radius ) / 2.414);,其中 2.414 是 (180 - 45) / 2 的正切值。

    let a = 67.5;
    const rad = Math.PI / 180;
    
    console.log((Math.tan( a * rad)))
    *{margin:0;padding:0}
    
    
    .wheel_container {
      position: relative;
      
      --wheel-size: 360px;
      width: var(--wheel-size);
      height: var(--wheel-size);
      
      margin-bottom: 2.4em;
    }
    
    .wheel {
      display: flex;
      justify-content: center;
      
      position: relative;
      overflow: hidden;
      
      width: var(--wheel-size);
      height: var(--wheel-size);
      
      border-radius: 50%;
      background-color: aquamarine;
      --segment-deg: 45deg;
    }
    
    .wheel div {
      display: flex;
      justify-content: center;
      align-items: center;
      
      position: absolute;
      
      
      --radius: calc(var(--wheel-size) / 2 );
      height: var(--radius);
      
      width: calc( 2 * var(--radius ) / 2.414);
      clip-path: polygon(0 0, 50% 100%, 100% 0);
      
      transform-origin: bottom;
      writing-mode: vertical-rl;
    }
    
    .wheel div > span {
      font-weight: 500;
      font-size: 1rem;
      text-align: center;
      color: rgba(0, 0, 0, 0.7);
    }
    
    .wheel div:nth-child(1) {
      background-color: beige;
      transform: rotate(calc(-1 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(2) {
      background-color: blueviolet;
      transform: rotate(calc(-3 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(3) {
      background-color: crimson;
      transform: rotate(calc(-5 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(4) {
      background-color: orange;
      transform: rotate(calc(-7 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(5) {
      background-color: violet;
      transform: rotate(calc(-9 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(6) {
      background-color: yellow;
      transform: rotate(calc(-11 * var(--segment-deg) / 2));
    }
    
    
    .wheel div:nth-child(7) {
      background-color: red;
      transform: rotate(calc(-13 * var(--segment-deg) / 2));
    }
    
    .wheel div:nth-child(8) {
      background-color: blue;
      transform: rotate(calc(-15 * var(--segment-deg) / 2));
    }
    <div class='wheel_container'>
      <div class='wheel'>
        <div><span>Apple</span></div>
        <div><span>Durian</span></div>
        <div><span>Banana</span></div>
        <div><span>Mango</span></div>
        <div><span>Strawberry</span></div>
        <div><span>Jackfruit</span></div>
        
        <div><span>red</span></div>
        <div><span>blue</

    Antwort
    0
  • StornierenAntwort