CS 318: Lab 20 – Animations
Dear students,
Today we explore transitions to add a little life to our webpages using CSS transitions. As an example, we’ll create a list whose items pop out when hovered.
We start with a list:
<ul>
<li>one</li>
<li>two</li>
<li>three</li>
<li>four</li>
</ul>
Let’s add some background color to each item:
li {
background-color: blue;
color: white;
}
Let’s remove the bullets, shrink the size a bit, and decrease the padding:
ul {
list-style: none;
width: 200px;
padding-left: 0;
}
Let’s space things out a bit:
li {
/* ... */
margin: 10px auto;
padding: 20px;
}
Now let’s accentuate hovered list items:
li:hover {
background-color: purple;
transform: translate(20px, 0);
}
This is where transitions come in. In their absence, we move from hovered to non-hovered styles instantaneously. We want to smoothly traverse between the two states. We need to specify a few CSS properties to enable that blending:
transition-property
: the names of the CSS properties that we want to blendtransition-duration
: the time it takes for the transition to finishtransition-timing-function
: the “directness” of the blending
Let’s make the list items transition between their left
and background-color
properties over half a second. We’ll start and end the transition slowly:
li {
/* ... */
transition-property: transform, background-color;
transition-duration: 500ms;
transition-timing-function: ease-in-out;
}
We can also express this in shorthand notation:
li {
/* ... */
transition: transform 500ms ease-in-out, background-color 500ms ease-in-out;
}
Here’s your TODO list:
- Read CSS Transitions and Transforms for Beginners and chapter 11 in your textbook. On a quarter sheet, write down 2-3 questions, observations, or ideas for transitions you’d like to include in your client project.
- A week from today we have our first prototype due. It will be reviewed by your peers in class, and it should be functional and content-complete. Would you like to have a workday next class period to work through issues together?
See you next time!
Lab
Our goal today is to add some life to our web pages by adding in some animations via CSS transitions. We’ll animate a hand of playing cards and a flower garden.
First create a lab20
directory. Add a partners.html
and include your first names and last initials.
Cards
Your first challenge is to create a selectable hand of cards interface that behaves as follows:
Follow these steps to produce your interface:
- Set all elements’
box-sizing
property toborder-box
. - Create a container
div
to hold the hand of cards. Give it classhand
. - Create five child
label
s withinhand
, each of classcard
. - Within each
card
, place a checkbox element followed by animg
element. Have the image show a playing card of your choosing. These card images are in the public domain. No classes or IDs are needed for these elements. - Shrink the cards. Set
card
to have a fixed width in pixels of your choosing. We’ll refer to that width as W. Set the images to be as wide as their parent element. But don’t use W—use a percentage. - Overlay the checkbox on the bottom-left corner of the card. Recall that we use absolute positioning to anchor elements relative to their parents. Let
card
serve as an anchorable parent by making it relatively positioned. Then absolutely positioninput[type="checkbox"]
against the bottom left of its parent. Add some spacing for aesthetics. - You may or may not see the checkboxes disappear after you absolutely position them. Probably they are behind the images. The front-to-back order of stacked HTML elements is determined by the
z-index
property. The larger thez-index
number, the closer to the viewer the element is. The particular numbers are not important, only the relative order. Set thez-index
of both the images and the checkboxes so that the checkbox is frontmost. - Overlap the cards. We’ll use absolute positioning to achieve this. Each card will be a bit more inset from its parent than the previous card. Set the positioning of
hand
to be relative so it can serve as an anchoring parent. Switch the positioning ofcard
toabsolute
. Then set theleft
properties of each of the individual cards. The first card should have no offset. Inset the second by half of a card—which is half of W. Inset the third by a full card, and so on. To apply rules to individual cards, don’t add IDs. Use thenth-child
selector. - Center
hand
. It’s a block element, so centering is done by constraining the width to something less than the full page and setting the left and right margin toauto
. How wide shouldhand
be to contain its children? You can calculate this exactly based on W. - Animate the selected cards to slide down from the hand when they are clicked on. (Because an image is part of a checkbox’s
label
element, we can click anywhere on the card to check it.) This will take a few steps to get right. First, write a transition rule for checked checkboxes that pushes the checkbox down. Use this pseudoselector:input[type="checkbox"]
. Set thetransform
property totranslate(0, OFFSET)
—whereOFFSET
is some number of pixels of your choosing. Set thetransition
property so it animates to this transform. - The previous step only animated the checkbox, but not the image. In a perfect world, we could write a rule that shifted the entire parent
card
that surrounded a checked checkbox. Unfortunately, CSS does not currently support selecting the parent of some specified child element. However, we can select the immediate sibling with the+
operator. To select ab
that immediately followsa
, we writea + b
. Extend the rule you wrote in the previous step to apply both to the checkbox and to theimg
that follows the checked checkbox. Recall that we target a list of selectors by separating them with commas. We want something of this form:a, a + b
. After this, both the checkbox and image should slide down. - When you unselect the card, it probably snaps immediately back into its default location. That’s a little too abrupt. Let’s also set the transition out. Write another rule nearly identical to the one you just wrote, but remove the
:checked
pseudoselector and zero out the offset. This rule will need to appear before the:checked
version; otherwise it will override the checked version. When two rules have the same specificity—as these two do—whichever appears last wins.
Flowers
Create in flowers.html
and flowers.css
an interactive floral arrangement that uses CSS transforms and transitions to ensnare the viewer in a state of blissful bee-ness:
Observe these requirements:
- Set all elements’
box-sizing
property toborder-box
. - Create a
div
with IDflowerbed
. - Download and unzip these flower icons, courtesy of Freepik. The license of these images require attribution, which we will attend to later.
- Add sixteen
img
elements toflowerbed
for each of these images. Not all the files have the same resolution, which will frustrate our perfect 4×4 grid. Use CSS to uniformly set each image to a 129×129 square. Add a 10-pixel margin all around to space them apart a bit. - To get the images to form a grid with no additional HTML markup, have them all float left. To break them up into rows, we need the images in the first column to clear the ones previous. However, don’t create special IDs or a special class for this. Use an
nth-child
selector. Recall that one can match a numeric cycle using a form of this selector:...:nth-child(An+B) { /* ... */ }
A
represents the length of the cycle’s period. For example,3n
would match every third child: 3, 6, 9, 12, and so on.B
lets us tack on an offset.3n+2
would match children 2, 5, 8, 11, 14, and so on. In our case, we want to match children 1, 5, 9, and 13 and have those clear their predecessor floats. (Child 1 will have nothing to clear.) What period and offset do we want to use here? - When an image is not hovered but another image is, reduce its opacity to 10%. It might be tempting to use the sibling selector (
~
) for this. Go ahead and watch it fail:As you should see, the sibling selector only matches images after the hovered image. It’s really a subsequent sibling selector. What we can do instead is use a descendant selector. Select all images that are children of a hoveredimg:hover ~ img { /* ... */ }
flowerbed
and reduce their opacity to 10%. - But we want the image that is hovered over to stay at its full opacity. Add a rule for this. If this new rule doesn’t seem to have any effect, it may not have a high enough specificity to beat out the 10% rule.
- Augment your hovered image rule to scale the image 1.5 times its normal size and rotate it 180 degrees. Consult MDN’s documentation on the
transform
property. - Set the image to transition smoothly between its hover and non-hovered
opacity
andtransform
properties. Ease the transition in and out over a span of 2 seconds. Since we’ve got multiple properties that we want to transition, the CSS is cleaner if you set thetransition-
properties separately. If you use the shorthand notation, you have to repeat the durations and timing functions. That’s not fun. Instead, set the standalonetransition-duration
andtransition-timing-function
properties to the single value shared by each transition. Settransition-property
to the list of properties to animate. - In your testing, you should find that sometimes the non-hovered flowers appear on top of the hovered one. If you don’t see this, increase the non-hovered opacity temporarily so that you can see it. This happens because the browser renders subsequent elements on top of previous elements. We can force a different ordering using the
z-index
property. Set thez-index
of your images in their hovered and non-hovered states so that hovered images appear on top of non-hovered images. Addz-index
to your list of transition properties. Forz-index
to have any effect, the element must not be statically positioned. Use relative positioning instead. - Center
flowerbed
within the webpage, both vertically and horizontally. The width-margin technique doesn’t work for vertical centering, so don’t use it here. Instead, use absolute positioning onflowerbed
. Anchor its top-left corner to 50% point of its parent. Then translate it up and left -50% to compensate. - The license of the icons requires attribution. Add the message “Icons courtesy of Freepik” and have it link to their website: http://www.freepik.com. Anchor the link to the bottom-right of the page.
Publish and Validate
Commit and push your work. Verify that all pages have been uploaded by visiting https://USERNAME.github.io/cs318/lab20
in your browser.
Validate your pages with the W3C Validator. Paste in the URLs to your pages, one at a time, and address all concerns raised by the validator. Fix your changes on the local machine, commit, and push until the validator reports no errors or warnings.