Award-Winning Marketing Websites

Animating Variable Fonts with Mouse Events

Award-Winning Marketing Websites

Lesson Description

The "Animating Variable Fonts with Mouse Events" Lesson is part of the full, Award-Winning Marketing Websites course featured in this preview video. Here's what you'd learn in this lesson:

Matias demonstrates the flexibility of web font weights and explains why designers might want to animate the font-weight CSS property dynamically. He uses the useEffect hook to track the mouse position and update a CSS variable based on the distance the mouse is from the center of the screen.

Preview

Transcript from the "Animating Variable Fonts with Mouse Events" Lesson

[00:00:00]
>> Matias Gonzalez: OK, let's talk a little bit more about variables. We're going to talk about two different topics here. One is a little bit more deep dive into CSS variables, and another topic that I really like is font variables, variable fonts. So before, when you used a font, you usually have like a preset of weights, so you will have like a thin font and then the regular and then bold and extra bold, and that was it, but nowadays, fonts have like variable axes, so let's go for example into this font.

[00:00:41]
And it's going here in the type tester, let's increase the font size to something way larger. And as I can see nowadays in tools like Google Fonts we have sliders so it's not that we have 3 or 4 predefined font weights we actually have a range that we can modify and this can, as you are seeing here, this can be dynamically animated on a website so this can be like a really interesting and useful thing to use.

[00:01:19]
So let's see how we can use that and animate it, also using CSS. OK, so I have my font here. The way you would load the font in CSS is using the font module. So here on the layout, I have loaded this font called Montserrat, and you probably always want to specify a subset. So like you don't want to download the entire font if you know you're just using the Latin characters.

[00:01:50]
And you also want to specify the variable weight so you could download a specific weight of the font but just a variable font is better because you can just have all of the weight at once it's like a dynamic program that you can use. And then to specify the weight of a variable font you would use on CSS the font variation settings and you will specify things like the weight, for example, so as I can see right now it has 200 of weight and if I change it to something like 900 I would see that immediately gets like bolder and I can do things in the middle like 450, and I have like a continuous range so let's actually animate this using CSS.

[00:02:45]
The effect that I want to do is I want to take the position of my mouse and the closer I move my mouse to the text, I want it to get like thinner and more spaced to like react to the mouse movement. So let's first, how can we like measure the position of a mouse? The simplest way is just to add the useEffect and attach a callback to the mouse move listeners, so let's say window.addEventListener and mouse move.

[00:03:29]
And then let's like add a callback. In here well, mouse, OK. So the first thing we need to remember with React is that we need to clean up our effects because if I go into the console I can see that this callback is being called. But if I go to another page, the callback is still there, it's not going to be deleted just because I left the page.

[00:04:06]
So one way is to, as we're used to just removing event listeners and like pass the callback and that but that can get like a little too boilerplate, if we have multiple listeners. It happens sometimes that you have like multiple listeners and then you have to clean up all of those listeners on your return function. So in JavaScript there is an easier way to clean up callbacks, and it's called an abort controller, so let's actually use that.

[00:04:45]
So const controller is equal to new AbortController. And this controller is something that we can just do controller.abort on our return. And we can access like, hey, this controller is aborted or not through the signal, so controller.signal.aborted. This will tell us if this controller is still active or not. So this is something we can use well like attaching callbacks and then we want to like cancel the callback somewhere else so this class is really, really useful for that and in the event listeners, there is actually another parameter that we can pass in with options.

[00:05:36]
And what we can do here is connect this controller to the listeners, so I would go and say the signal is the controller.signal. So whenever we go ahead and abort this controller, this event listener is going to be removed, basically. So this is really useful for when you are like adding a bunch of listeners for different things and then you just want to clean them all together, having a controller is actually really useful for that.

[00:06:11]
So let's test that it is working, so I'm moving the mouse and then I get away and I'm not moving the mouse anymore. I mean I am moving the mouse but it's not calling the callback. Let's actually calculate how far away my mouse is from the center of the screen, or from a specific point on the screen. This is usually useful for like adding different effects related to the mouse, so let's grab the event from the mouse movement and in order to access where the mouse is, I can access the clientX and clientY properties, so I'm going to say const mouseX is equal to event.clientX and const mouseY is equal to event.clientY.

[00:07:06]
I also want to make sure like how much the screen, how big the screen is in pixels, so I can just access that using the window property, so const screen width equal to window.innerWidth and const screen height equal to window.innerHeight. So the middle of my screen is going to be the half of the screen width. So we want to divide this number by 2.

[00:07:57]
And let's call that centerX to be more clear and centerY it's going to be the screen height divided by 2. So now we have 2 points. And I want to measure the distance between those two points in order to make things easier. I added some math utilities to the repository and in here we have a simple function to calculate distance. So I can say, let's calculate the distance between the mouse and the center of the screen, let's say const d is equal to distance.

[00:08:43]
And I'm going to import that from the math utilities. And let's pass mouseX, mouseY. And then the second point, it's going to be the center of the screen, so centerX and centerY. If I log this, I should see a value that approaches 0 as I approach the center of the screen, so it gets smaller and smaller, it's actually rounded to make it easier to read.

[00:09:15]
And let's increase a little bit the font size in here. So as I approach the center of the screen, this value gets smaller and smaller, and as I approach the corner, which will be like the furthest point that we could be, this value is going to be bigger. One little thing that I need to solve here is that this value depends on the width of my screen.

[00:09:39]
So if I have like a mobile device, this value will be smaller, and if I have like a 4K screen, this value will be like huge. So I want to normalize this value. I want it to be zero when I am at the center of the screen, and I want it to just be 1 when I am at the corner. So that's usually how you go about like calculating like distances you want to like normalize the value based on some measurement.

[00:10:10]
So let's actually measure how much is this distance and we already have a utility for that. We have the distance utility. So what we can do is we could measure the distance from a corner to the center and that will give us like the max length on this specific screen. So let's call a constant maxDistance is equal to the distance between, I don't know, 0 and 0, so a corner of the screen and then the centerX and centerY.

[00:10:47]
So if I divide my distance by the maximum distance possible, I would just get a value between 0 and 1, and since we're rounding it, it doesn't really make sense so it's just. So right now this value is going to approach 0 as I get close to the center of the screen and then approach 1 as I go into the corner and it doesn't matter like my screen size it's just going to be always normalized.

Learn Straight from the Experts Who Shape the Modern Web

  • 250+
    In-depth Courses
  • Industry Leading Experts
  • 24
    Learning Paths
  • Live Interactive Workshops
Get Unlimited Access Now