Flipping A Card With HTML, CSS, & JavaScript

Flipping the Queen of HeartsIt is possible to create 3D graphics on the web. It should be even better as browsers improve. As an example, the “model” HTML tag has lots of potential. But what if you don’t want to wait, or what if you want something extremely lightweight? For flipping cards, simple CSS can create a sense of perspective. That’s what this tutorial is about.

Well, it’s actually a bit more complicated than just flipping cards. It’s sorta a game — a card matching game. If you’ve played Super Mario Bros. 3, or seen memory card games for kids, you’ve probably seen this game before. The idea is simple… match two of a kind.

Expand View

Two cards can be selected. If there’s a match, they stay visible. If there isn’t a match, the cards get flipped back to hidden. In the comments section of a Photics.TV (YouTube) video, it was asked if it was possible to build such a game with Tumult Hype. It is possible, but I preferred using pure HTML, CSS, and JavaScript for this project. When index.html, web-10.css, and web-10.js are added together, it’s a mere 5K of data. That’s way smaller than the Hype runtime.

Emoji are used as a placeholder, which also keeps the project lightweight. Pictures could have been added, but the use of emoji sets up another tutorial — how to display emoji on Raspberry Pi OS.

Even though this is a basic project, it can branch out into lots complicated topics. That’s why the focus is merely flipping the cards. JavaScript is used for interactivity.

document.getElementById("Group").addEventListener("click", click);

To briefly summarize, an event listener is listening for clicks in the “Group” element. If the back of a card was clicked, and that card is playable, then the card is flipped. This is accomplished with the “flip” function.

function flip(n) {
     document.getElementById("Front-" + n).classList.toggle("Flip");
     document.getElementById("Back-" + n).classList.toggle("Flip");

A card is actually two HTML elements stacked on top of each other. They use CSS transforms to face opposite directions. That’s the importance of CSS. There are three main parts…

transition: transform ease-out 0.5s;

To add animation, both the front and back elements use transitions. Whenever a transform is changed, it will “ease-out” to the new setting with a half-second (0.5s) transition.

But, that’s just decoration. The two lines before this are critical…

     -webkit-backface-visibility: hidden;
     backface-visibility: hidden;

This is a wonderful option in CSS that can help to create a sense of space. Normally if you just flip an element 180°, then the view is reversed. That’s not how cards work. They’re supposed to be hidden if not facing you. That’s the beauty of “backface-visibility”. If the element is not facing you, it can be hidden.

But to make an element face another direction, it needs to be given an X rotation angle or Y rotation angle that is away from view. That’s why the front of the card is spun right at the start. It has a default rotateY angle of -180°.

     transform: rotateY(-180deg);

Then, by toggling styles, the two elements can be rotated…

.Flip.Back {
     transform: rotateY(-180deg) !important;
.Flip.Front {
     transform: rotateY(-360deg) !important;

This transition could still look flat, which is why a “perspective” of 500 pixels is added to elements with the “card” style. Lower numbers can make the effect more dramatic. That’s why a value of “500px” was used. This avoids a problem with cards overlapping.

There is a lot going on, but the basic idea is to consider the potential of pure HTML, CSS, and JavaScript. Back when the Groundhog template was first created, visibility was being controlled with the Hype timeline. Using backface-visibility is an easier alternative.