W3C.US

  • Increase font size
  • Default font size
  • Decrease font size
Home Tutorial HTML5 Use css3 to creating a 3D sphere

Use css3 to creating a 3D sphere

E-mail Print PDF

With CSS3’s 3D trans-forms I’ve illus-trated how to build a cube and a tetra-he-dron. It is also pos-si-ble to cre-ate a sphere-like object, albeit with many elements.

3D CSS Sphere
Works in the lat-est Safari and iOS and Chrome.



Recently I’ve been look-ing at cre-at-ing applic-a-ble 3D carousels. These rely on posi-tion-ing pan-els in a cir-cle around a cen-tral point (ie. rota-tion about the Y-axis), I put these pan-els in an unordered list. A nat-ural exten-sion is to dupli-cate each <ul> and rotate about the X-axis. With ‘A’ rounds (or lists), and ‘B’ pan-els per round (<li>s), I built a script that would dis-trib-ute these in a cir-cu-lar man-ner, pan-els about Y-axis, lists about the X-axis, cre-at-ing a sphere.

The more ele-ments per round and the more rounds, the smoother the sphere. But this soon stacks up and kills Safari. The opti-mum num-bers have been about 9 rounds and 30 pan-els per round for a decent look-ing sphere, but that’s 279 3D ele-ments and Safari starts to choke. Allow-ing the pan-els to over-lap eases this some-what and leads to a tighter sphere but it still appears blocky.

The biggest gains come with bor-der radius. Using a huge radius that made each panel cir-cu-lar the sphere sud-denly gained a lovely cur-va-ture, and the num-ber of rounds and pan-els could be reduced. In the exper-i-ment I use 8 rounds and 24 pan-els (200 ele-ments). This doesn’t start chok-ing until I start aggres-sively animating.

Play-ing with this I’ve built a few dif-fer-ent styles of sphere. In the exper-i-ment I’ve included the blocky “square” ver-sion, along with the smoothed out bor-der radius one (default). Mark-ing pan-els white, and a few black can cre-ate a nice eye-ball effect.

Also included in the exper-i-ment are ver-sions show-ing a sin-gle round and another style named “con-tact”. This takes two lists and ani-mates them like the space trans-porta-tion device in the Jodie Fos-ter movie of the same name.

Ani-mat-ing the bor-der radius on all 192 pan-els (if your machine can cope), gives a neat kalei-do-scope effect, also included in the experiment.
Code

The gen-er-ated HTML is sim-ply a cou-ple of <div>s con-tain-ing lists:

<div id="sphere">
<div class="container">
<ul>
<li></li>
<li></li>
</ul>
</div>
</div>


To trans-form each set of pan-els into a cir-cle the total num-ber is divided by 360 to get the angle of rota-tion. Merely rotat-ing will put all pan-els on top of each other, trans-lat-ing in the Z axis will move them out from the cen-tre point. The cor-rect trans-la-tion dis-tance so the pan-els slightly over-lap (i.e. the cir-cle radius) is worked out with some sim-ple trigonom-e-try. Lists are rotated in the X axis, sim-ply the num-ber of lists divided by 360.

Loop-ing through each panel for each list, the angles of rota-tion are grad-u-ally increased by the cal-cu-lated incre-ments and applied to the elements:

var panels = p || this.panels,
rounds = r || this.rounds,
rotationPerPanel = 360/panels,
rotationPerRound = 360/2/rounds,
yRotation, xRotation,
width = this.panelWidth,
zTranslate = (width/2) / Math.tan(rotationPerPanel * Math.PI/180),
$container = this.el,
$ul, $li, i, j;

this.el.html('');
for(i = 0; i < rounds; i++) {
$ul = $('<ul>');
xRotation = rotationPerRound * i;
$ul[0].style.webkitTransform = "rotateX("+ xRotation + "deg)";
for(j = 0; j < panels; j++) {
$li = $('<li>');
yRotation = rotationPerPanel * j;
$li[0].style.webkitTransform = "rotateY("+ yRotation +"deg)
translateZ("+ zTranslate +"px)";
$ul.append($li);
}
$container.append($ul);
}


To achieve the 3D effect we give #sphere some per-spec-tive, which forms the con-tain-ing block. A sec-ond con-tainer tran-si-tions between dif-fer-ent trans-forms, let-ting us rotate the sphere. The com-pli-cated trans-form parts are applied inline via the JavaScript above, but each list ele-ment needs preserve-3d so its direct descen-dants are trans-formed in the same 3D space (rather than in 2D).

#sphere {
width: 100px;
height: 100px;
margin: 200px auto;
-webkit-perspective: 800;
}

.container {
width: 100px;
height: 100px;
-webkit-transition: -webkit-transform 200ms linear;
-webkit-transform-style: preserve-3d;
}

.container > ul {
-webkit-transform-style: preserve-3d;
width: 100%;
height: 100%;
position: absolute;
}

.container li {
width: 98px;
height: 98px;
position: absolute;
display: block;
background: #000;
border: 1px solid #fff;
opacity: 0.1;
border-radius: 50px;
}

The original post: http://www.paulrhayes.com/2011-02/creating-a-sphere-with-3d-css/

The demo link: http://www.paulrhayes.com/experiments/sphere/

Last Updated on Tuesday, 02 August 2011 03:44