In todays lesson we made a kind of Image editor to control padding, color and blur. The lesson mainly focusses on the use of CSS variables and how we can change them using JavaScript.
Lessons Learned
-I learned about a new input type, 'range', which is basically a slider that has a default “value” a min value and max value.
<input
id="spacing"
type="range"
name="spacing"
min="10"
max="200"
value="10"
data-sizing="px"
/>
<label for="blur">Blur:</label>
<input
id="blur"
type="range"
name="blur"
min="0"
max="25"
value="10"
data-sizing="px"
/>
Notice that the min and max values have to be in quotes.
-I learned about another input type, called color.
<label for="base">Base Color</label>
<input id="base" type="color" name="base" value="#ffc600" />
</div>
So what's so good about CSS variables you may ask. Specially when we've had variables in SAAS forever. The key difference and advantage of CSS variables is that the can be updated using JS meaning that when you update a variable in CSS, everywhere on the page that that variable is referenced will update itself unlike in SAAS where we define the variables at compile time, then they get compiled and we can't change them.
The way CSS variables work is that you declare them on some sort of element, in our case we are going to declare it on root, which is sort of the highest level you can get (very similar to declaring it on the HTML element) and this is where we will set the default values for our variables.
The syntax is a bit odd we have to use -- as a prefix and while using them use the prefix var and then write the variable name inside parenthesis prefixed by the --.
:root {
--base: #ffc600;
--spacing: 10px;
--blur: 10px;
}
img {
padding: var(--spacing);
background: var(--base);
filter: blur(var(--blur));
}
.hl {
color: var(--base);
}
Changing the CSS variables using JS
-first thing we have to do is select all 3 input types we have used so that when they change, we can update the CSS variables which in turn will update all elements where the variables are used.
const inputs = document.querySelectorAll(".controls input");
This will return a NodeList of all the inputs that we have used.
-Now we'll loop over the entire list using forEach and listen for a change in input.
inputs.forEach((input) => input.addEventListener("change", handleUpdate));
-The change event listener will not be enough as we want to trigger change not only when we let go but also when we slide (move the mouse). So we'll add a mouseover event as well.
inputs.forEach((input) =>
input.addEventListener("mousemove", handleUpdate)
);
- Now inside the handleUpdate function that we are calling everytime and event is triggered, first thing we need to know is what is the suffix of the value we are working on. Why? because spacing/blur they are going to return values like 10/20 but we actually need is 10px/20px otherwise the values won't be changed. So for that we use data attribute (
data-sizing="px"
) to store the suffix in spacing and blur input but not in base as it does not have a suffix, it's just a hex code.
-now we use dataset which is an already existing object (we don't have to select it or use attribute selectors from it). dataset is an object consisting of all the data attributes from that specific element.
this.dataset
returns all the “data” prefixed properties and their values.
- we use dataset to get our suffix and as a fallback value we use empty string to avoid getting undefined in case of base where there is no suffix.
const suffix = this.dataset.sizing || "";
-Now to update the variables we first have to select the variables and for that we select our entire document which is our root here and we're going to set a property of name="base/blur/spacing" beforehand in our attributes and we named our variables exactly that.
name="blur"
name="base"
name="spacing"
- finally we change the values using js
document.documentElement.style.setProperty(
`--${this.name}`,
this.value + suffix
);
What is documentElement?
From MDN, we find out:
document.documentElement returns the root element of the document for example, the HTML element for HTMLdocuments.
style.setProperty() takes in the name of the property, for example, the “name” attribute assigned to an input, in our case spacing|blur|base, and takes in the value for that element, as in, the value assigned to the “value” attribute in that element. The value also must have a unit-suffix if it applies (like px, s, pt, etc.) which we already stored in suffix variable.
GitHub Repo:
Thank You!
Top comments (6)
Nice👍
thanks.
You can add a feature in which I can upload my own image and apply filters.
I would definitely hold onto that idea for the future.
WELL , A GOOD TECHNIQUE ,for getting ready for open source contribution
Learn_and_Let_Learn
that is the goal.