---
# System prepended metadata

title: Tailwind and Classnames Basics
tags: [Tailwind]

---

# Tailwind

## Introduction

[Tailwind CSS](https://tailwindcss.com/docs/installation) is a "utility-first CSS framework".Tailwind provides hundreds of built-in classes that eliminate the need to start from scratch when creating designs. 

Tailwind also uses [PurgeCSS](https://v2.tailwindcss.com/docs/optimizing-for-production) to remove unused classes in production, resulting in a smaller bundle size.

If you've used Bootstrap before, you'll find Tailwind easy to pick up since a lot of the classes used are similiar.

## Basic Example

CSS
```typescript
<div style={{ width: '12px', height: '12px', backgroundColor: '#fe1b1b' }}></div>
```

Tailwind
```typescript
<div className='w-3 h-3 bg-red-500'>...</div>
```

## Breakpoints

Tailwind is utilizes a [mobile-first design](https://tailwindcss.com/docs/responsive-design).

```typescript
<p className="pt-3 text-sm md:text-base xl:text-lg">...</p>
```

## Hover, Focus, and Other States

Every utility class in Tailwind can be applied conditionally by adding a [modifier](https://tailwindcss.com/docs/hover-focus-and-other-states).

```typescript
<p className="bg-sky-500 hover:bg-sky-700 ">...</p>
```

These modifiers can even be stacked to target more specific situations.
```typescript
<p className="bg-sky-500 md:hover:bg-sky-700 ">...</p>
```

## Arbitrary Values

What if you want to use a style that's not in the default Tailwind classes? And it's only seldom used, so you don't want to add it to our custom Tailwind config?

This is where Tailwind's [arbitrary values](https://tailwindcss.com/docs/adding-custom-styles#using-arbitrary-values) come into play.

```typescript
<p className="text-[28px] bg-[#6aa700]">...</p>
```

**Note:**
- Before you use an arbitray value, **please make sure that the value you need isn't in the Tailwind default classes or our custom Tailwind Config first**.
- If you find that the arbitrary values **will need to be used a lot** in the future, **please add it in our custom Tailwind Config**.

## Important Modifier

You can make any utility **important** by adding a `!` character to the beginning:
```typescript
<p className="font-bold !font-medium">...</p>
```

This is useful when we need to override old Bootstrap classes.

## Grid Example
![](https://hackmd.io/_uploads/BygIPZD2h.png)

```typescript
<div className="h-[800px] flex items-center justify-center">
    <div className="grid grid-cols-3 gap-4 p-4 bg-green-500 w-[300px] h-[500px]">
        <div className="row-span-2 bg-green-300">1</div>
        <div className="bg-green-300">2</div>
        <div className="row-span-2 bg-green-300">3</div>
        <div className="bg-green-300">4</div>
        <div className="col-span-3 bg-green-300">5</div>
    </div>
</div>
```

## Grid example with Breakpoints

![](https://hackmd.io/_uploads/SyPjvZPnh.png)

```typescript
<div className="h-[800px] flex items-center justify-center">
    <div className="md:grid grid-cols-3 gap-4 p-4 bg-green-500 w-[300px] h-[500px]">
        <div className="row-span-2 bg-green-300">1</div>
        <div className="bg-green-300">2</div>
        <div className="row-span-2 bg-green-300">3</div>
        <div className="bg-green-300">4</div>
        <div className="col-span-3 bg-green-300">5</div>
    </div>
</div>
```

## Config

By default, Tailwind will look for an optional [tailwind.config.js](https://tailwindcss.com/docs/configuration) file at the root of your project where you can define any customizations.

### Content

Because we currently use Bootstrap as well as Tailwind in our USA project (we are planning to phase-out Bootstrap but it takes time), if we enable Tailwind globally it will mess up the formatting in some places.

Thus, if we add a new new page/component that needs Tailwind, we have to add it to the **Content** section:

![](https://hackmd.io/_uploads/HkYsXNj3n.png)

**Glob Basic Syntax**

Tailwind uses [fast-glob](https://github.com/mrmlnc/fast-glob) for pattern matching.
- An asterisk (`*`) — matches everything except slashes (path separators), hidden files (names starting with `.`).
- A double star or globstar (`**`) — matches zero or more directories.

**Examples**

Say your file structure looks like this:
```
🗀 components
   🗀 blog
      🗀 categories
         🞍 categories-list.tsx
         🞍 categories-link.tsx
      🞍 container.tsx
      🞍 metadata.tsx
   🗀 faq
      🞍 search-result.tsx
      🞍 search.tsx
   🞍 footer.tsx
   🞍 modal.tsx
🗀 pages
🞍 tailwind.config.js
 
```

- `./components/blog/**/*.{tsx,jsx,js}` — matches all files in the **components/blog** directory (any level of nesting) that have the extension **tsx**, **jsx**, or **js**.
- If you want to specify just one file for example, you can write `./components/blog/categories/categories-link.tsx`


### Screens

In **theme** > **screens**, we can customize our breakpoints:

![](https://hackmd.io/_uploads/rkVh5-v33.png)

### Colors

In **theme** > **extend** > **colors**, we can customize our colors:

![](https://hackmd.io/_uploads/r15boZv22.png)

### Important Note

- Notice how **colors** is placed within **extend**. Any config that is under **extend** means that **it is extended from the default config**. 
- If it's not under **extend**, it will **override the default config** and we usually don't want that.
- So please make sure to add **any new config options under extend**.
![](https://hackmd.io/_uploads/rkJXa-D2h.png)

## Homework

In our **iBuypower.NextJS** project, go to branch **playground**.

Write the code for Homework 1 and 2 here:
- pages\playground\hw-1.tsx
- pages\playground\hw-2.tsx

Work task: IUW-369

### Homework 1 - Tailwind Grid Layout (no RWD required)

![](https://hackmd.io/_uploads/SkTzfzvhh.png)

### Homework 2 - Tailwind Grid Layout (with RWD)

Mobile view

![](https://hackmd.io/_uploads/S1MdHzDh3.png)

Tablet view

![](https://hackmd.io/_uploads/B1HXIzDhh.png)

Desktop view

![](https://hackmd.io/_uploads/SJQ38Mw3h.png)

## Official Docs

- https://tailwindcss.com/docs/installation

---

# Classnames

## Introduction

[Classnames](https://www.npmjs.com/package/classnames) is a simple JavaScript utility for conditionally joining classNames together.

## Usage

Basic examples of different usage:

```typescript!
classNames('foo', 'bar'); // => 'foo bar'
classNames('foo', { bar: true }); // => 'foo bar'
classNames({ 'foo-bar': true }); // => 'foo-bar'
classNames({ 'foo-bar': false }); // => ''
classNames({ foo: true }, { bar: true }); // => 'foo bar'
classNames({ foo: true, bar: true }); // => 'foo bar'

// lots of arguments of various types
classNames('foo', { bar: true, duck: false }, 'baz', { quux: true }); 
// => 'foo bar baz quux'

// other falsy values are just ignored
classNames(null, false, 'bar', undefined, 0, 1, { baz: null }, ''); // => 'bar 1
```

Usage with React, Tailwind, and TypeScript:

```typescript!
import cn from 'classnames';

export default function ItemCard({ text, isShown = true, variant = Variant.THIN }: IItemCardProps) {
    return (
        <div
            className={cn('mx-auto bg-lime-400', {
                'w-80 text-sm': variant === Variant.THIN,
                'text-md w-96 font-bold': variant === Variant.FAT,
                'hidden': isShown === false,
            })}
        >
            <p>{text}</p>
        </div>
    );
}

export enum Variant {
    THIN = 'THIN',
    FAT = 'FAT',
}

interface IItemCardProps {
    text: string;
    isShown?: boolean;
    variant?: Variant;
}

```

# Other

- $projects and config
- eslint and prettierr
- file naming
- const
- API proxy, endpoints, services
- redis
- preventXSS
- assgined jira work tasks
  => explain work task specs, create new branch, git commit message, how to mark progress, QA, deploying,
- answer questions
