Documentation
Feedback
Guides
Learning Center

Learning Center
Learning Center
Modifying the countdown block to have configurable styles
View in Portuguese
This content was migrated from the VTEX Learning Center and is no longer being actively maintained. For the most accurate and up-to-date information, please check the official documentation.

Introduction

Now that we have implemented the countdown, how about adding a little customization? In this step, you will learn basic concepts about CSS handles and Tachyons to customize the style of your app.

CSS Handles

CSS handles are used to customize your store's components through CSS classes in the theme code. All settings are defined through the app vtex.css-handles, which is responsible for declaring all the customization points of your block.

By defining the names of your handles and adding them to their respective HTML elements, you can give the theme's users customization points that allow them to create flexible layouts.

Tachyons

Tachyons is a framework for functional CSS. Unlike other known frameworks, like Bootstrap, it does not have "pre-built" UI components. In fact, its purpose is, precisely, to separate the CSS rules into small, reusable parts. This type of strategy is commonly known as Subatomic Design System, and if you are interested, you can find a reference for it in this link. This strategy makes frameworks like Tachyons very flexible, scalable, and fast.

Many of the Tachyons' definitions can be changed so that your store has a more customized style. To do this, just define a JSON file in the styles/configs folder; this information can be found in more detail at Customizing styles on VTEX IO.

Customizing your block

  1. First, import the useCssHandles hook. To do so, return to Countdown.tsx and do the import:


    _10
    // react/Countdown.tsx
    _10
    import { useCssHandles } from 'vtex.css-handles'

  2. Now, define in a Array all necessary handles (in this case, only 'countdown' will be used):


    _10
    // react/Countdown.tsx
    _10
    const CSS_HANDLES = ['countdown']

  3. After defining the array, let's use the useCssHandles in the component Countdown to define the countdown handle:


    _20
    // react/Countdown.tsx
    _20
    const Countdown: StorefrontFunctionComponent<CountdownProps> = ({ targetDate = DEFAULT_TARGET_DATE }) => {
    _20
    const [timeRemaining, setTime] = useState<TimeSplit>({
    _20
    hours: '00',
    _20
    minutes: '00',
    _20
    seconds: '00'
    _20
    })
    _20
    _20
    + const handles = useCssHandles(CSS_HANDLES)
    _20
    _20
    tick(targetDate, setTime)
    _20
    _20
    return (
    _20
    <div>
    _20
    <h1>
    _20
    { `${timeRemaining.hours}:${timeRemaining.minutes}:${timeRemaining.seconds}` }
    _20
    </h1>
    _20
    </div>
    _20
    )
    _20
    }

  4. Finally, the handle in the component needs to be used to see the customization. For this, use the prop className with the classes to be used and the Tachyons classes, for global styles.


    _21
    // react/Countdown.tsx
    _21
    import React from 'react'
    _21
    ...
    _21
    _21
    const Countdown: StorefrontFunctionComponent<CountdownProps> = ({ targetDate = DEFAULT_TARGET_DATE }) => {
    _21
    const [timeRemaining, setTime] = useState<TimeSplit>({
    _21
    hours: '00',
    _21
    minutes: '00',
    _21
    seconds: '00'
    _21
    })
    _21
    _21
    const handles = useCssHandles(CSS_HANDLES)
    _21
    _21
    tick(targetDate, setTime)
    _21
    _21
    return (
    _21
    + <div className={`${handles.countdown} c-muted-1 db tc`}>
    _21
    {`${timeRemaining.hours}:${timeRemaining.minutes}:${timeRemaining.seconds}`}
    _21
    </div>
    _21
    )
    _21
    }

Let's see the result?

{"base64":"  ","img":{"width":3812,"height":1928,"type":"png","mime":"image/png","wUnits":"px","hUnits":"px","length":1350520,"url":"https://user-images.githubusercontent.com/19495917/75475280-457cab80-5977-11ea-938e-d3c2b532e891.png"}}

{"base64":"  ","img":{"width":1680,"height":1292,"type":"gif","mime":"image/gif","wUnits":"px","hUnits":"px","length":108504,"url":"https://user-images.githubusercontent.com/19495917/75475388-7a88fe00-5977-11ea-9d35-c13482f1e61c.gif"}}

Answer sheet

See answer sheet for Countdown.tsx
Countdown.tsx

_49
// store-block/react/Countdown.tsx
_49
import React, { useState } from 'react'
_49
import { TimeSplit } from './typings/global'
_49
import { tick, getTwoDaysFromNow } from './utils/time'
_49
import { useCssHandles } from 'vtex.css-handles'
_49
_49
interface CountdownProps {
_49
targetDate: string
_49
}
_49
_49
const DEFAULT_TARGET_DATE = getTwoDaysFromNow()
_49
_49
const CSS_HANDLES = ['countdown']
_49
_49
const Countdown: StorefrontFunctionComponent<CountdownProps> = ({
_49
targetDate = DEFAULT_TARGET_DATE,
_49
}) => {
_49
const [timeRemaining, setTime] = useState<TimeSplit>({
_49
hours: '00',
_49
minutes: '00',
_49
seconds: '00',
_49
})
_49
_49
const handles = useCssHandles(CSS_HANDLES)
_49
_49
tick(targetDate, setTime)
_49
_49
return (
_49
<div className={`${handles.countdown} c-muted-1 db tc`}>
_49
<h1>{`${timeRemaining.hours}:${timeRemaining.minutes}:${timeRemaining.seconds}`}</h1>
_49
</div>
_49
)
_49
}
_49
_49
Countdown.schema = {
_49
title: 'editor.countdown.title',
_49
description: 'editor.countdown.description',
_49
type: 'object',
_49
properties: {
_49
targetDate: {
_49
title: 'Data final',
_49
description: 'Data final utilizada no contador',
_49
type: 'string',
_49
default: null,
_49
},
_49
},
_49
}
_49
_49
export default Countdown

On this page