Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Rapid designing with Tailwind CSS

Rapid designing with Tailwind CSS

Component-focused CSS frameworks such as Bootstrap get you up and running quickly, but often lack the tools necessary for designing custom interfaces. For this people usually just use plain (S)CSS, which gets the job done but can become difficult to maintain in the long run.

Enter Tailwind, a utility-first CSS framework that approaches building complex components from a constrained set of primitive utilities. What sets Tailwind apart is the vast range of CSS properties it covers, a powerful PostCSS-backed configuration API and excellent documentation that explains CSS along the way. This talk will show Tailwind's unique approach to various aspects of design (spacing, colors, pseudo-classes, responsive design and more) and compare it with existing solutions.

Janko Marohnić

May 29, 2020
Tweet

More Decks by Janko Marohnić

Other Decks in Programming

Transcript

  1. Tailwind CSS
    Rapid designing with utility-first approach

    View full-size slide

  2. Janko Marohnić
    • Ruby developer
    • open source contributor
    • inexperienced in CSS
    • mainly used Bootstrap

    View full-size slide

  3. Tailwind CSS
    • utility-first CSS framework
    • maps closely to CSS properties
    • PostCSS plugin
    • created by Adam Wathan in 2017

    View full-size slide

  4. Bootstrap
    1 CSS
    2
    Tailwind
    3

    View full-size slide

  5. Utility-First

    View full-size slide





  6. Private Villa



    Relaxing All-Inclusive Resort in Cancun



    $299 USD per night



    View full-size slide

  7. .vacation-card {
    width: 16rem;
    margin: 0 auto;
    }
    .vacation-card-info {
    margin-top: .5rem;
    }
    .vacation-card-image {
    border-radius: .25rem;
    }
    .vacation-card-title {
    font-weight: 700;
    color: #4a5568;
    line-height: 1.375;
    }
    .vacation-card-eyebrow {
    font-size: .75rem;
    color: #718096;
    text-transform: uppercase;
    font-weight: 700;
    }
    .vacation-card-link:hover {
    text-decoration: underline;
    }
    .vacation-card-price {
    margin-top: .5rem;
    font-size: .875rem;
    color: #718096;
    }

    View full-size slide





  8. Private Villa



    Relaxing All-Inclusive Resort in Cancun



    $299 USD per night



    View full-size slide

  9. .vacation-card {
    width: 16rem;
    }
    .vacation-card-eyebrow {
    font-size: .75rem;
    color: #718096;
    }
    .vacation-card-title {
    color: #4a5568;
    line-height: 1.375;
    }
    .vacation-card-link:hover {
    text-decoration: underline;
    }
    .vacation-card-price {
    font-size: .875rem;
    color: #718096;
    }

    View full-size slide





  10. Private Villa



    Relaxing All-Inclusive Resort in Cancun



    $299 USD per night



    View full-size slide

  11. Embraces connection between
    HTML and CSS
    1

    View full-size slide

  12. No need to keep inventing
    new class names
    2
    .card-inner-outer-wrapper
    .container-wrapper-container
    .box-control-outer-container

    View full-size slide

  13. Localized styling
    makes changes safer
    3

    View full-size slide

  14. Your CSS stops growing
    4

    View full-size slide

  15. You’re designing with constraints
    5
    font-size: .875rem .text-sm
    color: #feb2b2 .text-red-300
    height: 100vh .h-screen

    View full-size slide

  16. Documentation teaches CSS

    View full-size slide

  17. Bootstrap Tailwind
    .d-block .d-inline-block .d-flex ... .block .inline-block .flex ...
    .justify-content-start
    .align-items-center
    .align-self-center ...
    .justify-start
    .items-center
    .self-center ...
    .text-uppercase
    .font-italic
    .font-weight-bold ...
    .uppercase
    .italic
    .font-bold ...
    .position-absolute
    .position-relative ...
    .absolute
    .relative ...

    View full-size slide




  18. Apple
    Apple
    ...





    Kiwi
    Kiwi
    ...


    page1.html
    page2.html

    View full-size slide




  19. {title}
    {text}
    ...



    Card.jsx
    Card.vue
    card.erb
    card.php
    ...
    page1.html

    page2.html

    View full-size slide




  20. {title}
    {text}
    ...



    Card.jsx
    Card.vue
    card.erb
    card.php
    ...
    page1.html

    page2.html

    View full-size slide

  21. .btn-blue {
    background-color: #4299e1;
    color: white;
    font-weight: 700;
    padding: 0.5rem 1rem;
    border-radius: 0.25rem;
    }
    Some Link

    ...
    Save

    View full-size slide

  22. .btn-blue {
    @apply bg-blue-500 text-white font-bold py-2 px-4 rounded;
    }
    Some Link

    ...
    Save

    PostCSS directive

    View full-size slide

  23. Spacing
    &
    Sizing

    View full-size slide

  24. .vacation-card {
    margin: 15px;
    padding: 18em;
    width: 77%;
    height: 16rem;
    }

    View full-size slide

  25. .m-*
    .mt-*
    .mb-*
    .ml-*
    .mr-*
    .mx-*
    .my-*
    Margin Padding
    .p-*
    .pt-*
    .pb-*
    .pl-*
    .pr-*
    .px-*
    .py-*
    Suffix Amount
    *-0
    *-1
    *-2
    *-3
    *-4
    *-5
    0
    0.25rem
    0.5rem
    1rem
    1.5rem
    3rem

    View full-size slide

  26. .m-*
    .mt-*
    .mb-*
    .ml-*
    .mr-*
    .mx-*
    .my-*
    Margin Padding
    .p-*
    .pt-*
    .pb-*
    .pl-*
    .pr-*
    .px-*
    .py-*
    Suffix Amount
    *-0
    *-1
    *-2
    *-3
    *-4
    *-5
    *-6
    *-8
    *-10
    *-12
    *-16
    *-20
    ...
    *-64
    0
    0.25rem
    0.5rem
    1.75rem
    1rem
    1.25rem
    1.5rem
    2rem
    2.5rem
    3rem
    4rem
    5rem
    ...
    16rem
    Width
    .w-*
    Height
    .h-*

    View full-size slide

  27. Class Property
    .w-25
    .w-50
    .w-75
    .w-100
    width: 25%
    width: 50%
    width: 75%
    width: 100%

    View full-size slide

  28. Class Property
    .w-1/2
    .w-1/3
    .w-2/3
    .w-1/4
    .w-2/4
    .w-3/4
    .w-1/5
    .w-2/5
    .w-3/5
    ...
    .w-11/12
    .w-full
    width: 50%
    width: 33.333333%
    width: 66.666667%
    width: 25%
    width: 50%
    width: 75%
    width: 20%
    width: 40%
    width: 60%
    ...
    width: 91.66667%
    width: 100%

    View full-size slide

  29. Phone Number




    View full-size slide

  30. Phone Number




    View full-size slide

  31. module.exports = {
    theme: {
    extend: {
    spacing: {
    '18': '4.5rem',
    }
    }
    }
    }
    ...
    .m-16
    .m-18
    .m-20
    ...
    ...
    .p-16
    .p-18
    .p-20
    ...
    ...
    .w-16
    .w-18
    .w-20
    ...
    ...
    .h-16
    .h-18
    .h-20
    ...
    ...
    4rem
    4.5rem
    5rem
    ...
    tailwind.config.js

    View full-size slide

  32. module.exports = {
    theme: {
    spacing: {
    'sm': '8px',
    'md': '12px',
    'lg': '16px',
    'xl': '24px',
    }
    }
    }
    tailwind.config.js
    m-sm
    m-md
    m-lg
    m-xl
    p-sm
    p-md
    p-lg
    m-xl
    w-sm
    w-md
    w-lg
    w-xl
    h-sm
    h-md
    h-lg
    h-xl

    View full-size slide

  33. #4b0082
    indigo
    rgb(76, 0, 130)
    rgba(76, 0, 130, 1.0)
    hsl(275, 100%, 25%)
    darken(#4b0082, 10%)
    lighten(#4b0082, 15%)
    tint(#4b0082, 20%)
    shade(#4b0082, 30%)
    ...
    ...

    View full-size slide

  34. *-primary
    *-secondary
    *-success
    *-danger
    *-warning
    *-info
    *-light
    *-dark
    ...
    .text-*
    .bg-*
    .border-*

    View full-size slide

  35. Taken from Refactoring UI

    View full-size slide

  36. Taken from Refactoring UI

    View full-size slide

  37. .text-red-300
    .bg-blue-500
    .border-green-700
    .btn-indigo {
    background-color: theme('colors.indigo.500');
    }
    PostCSS function

    View full-size slide

  38. module.exports = {
    theme: {
    colors: {
    indigo: {
    lighter: '#b3bcf5',
    default: '#5c6ac4',
    dark: '#202e78',
    }
    }
    }
    }
    tailwind.config.js
    .text-indigo-lighter
    .text-indigo-default
    .text-indigo-dark
    .bg-indigo-lighter
    .bg-indigo-default
    .bg-indigo-dark
    .border-indigo-lighter
    .border-indigo-default
    .border-indigo-dark

    View full-size slide

  39. const { colors } = require('tailwindcss/defaultTheme')
    module.exports = {
    theme: {
    colors: {
    indigo: {
    lighter: colors.indigo['300'],
    default: colors.indigo['500'],
    dark: colors.indigo['700'],
    },
    blue: {
    ...colors.blue,
    '900': '#1e3656',
    }
    }
    }
    }
    tailwind.config.js

    View full-size slide

  40. Pseudo-Classes

    View full-size slide

  41. Save
    .btn-blue { ... }
    .btn-blue:hover {
    background-color: #2B6CB0;
    }
    .btn-blue:focus {
    background-color: #2B6CB0;
    box-shadow: 0 0 0 3px rgba(66, 153, 225, 0.5);
    }

    View full-size slide


  42. Save


    Some Link


    Tab

    View full-size slide

  43. .hover\:bg-blue-500:hover {
    background-color: #4299e1;
    }
    .focus\:shadow-outline:focus {
    box-shadow: 0 0 0 3px rgba(66, 153, 225, 0.5);
    }
    .active\:text-indigo-300:active {
    color: #a3bffa;
    }

    View full-size slide

  44. @variants hover, focus {
    .hyphens-none {
    hyphens: none;
    }
    .hyphens-manual {
    hyphens: manual;
    }
    .hyphens-auto {
    hyphens: auto;
    }
    }
    PostCSS directive

    View full-size slide

  45. .hyphens-none { hyphens: none; }
    .hover\:hyphens-none:hover { hyphens: none; }
    .focus\:hyphens-none:focus { hyphens: none; }
    .hyphens-manual { hyphens: manual; }
    .hover\:hyphens-manual:hover { hyphens: manual; }
    .focus\:hyphens-manual:focus { hyphens: manual; }
    .hyphens-auto { hyphens: auto; }
    .hover\:hyphens-auto:hover { hyphens: auto; }
    .focus\:hyphens-auto:focus { hyphens: auto; }

    View full-size slide

  46. Responsive Design

    View full-size slide

  47. @media (min-width: 640px) { ... }
    @media (min-width: 768px) { ... }
    @media (min-width: 1024px) { ... }
    @media (min-width: 1280px) { ... }

    View full-size slide

  48. .col-sm-8
    .col-md-6
    .col-lg-4
    .col-xl-2
    .d-sm-block
    .d-md-inline-block
    .d-lg-flex
    .d-xl-none
    .flex-sm-row
    .justify-content-md-center
    .align-items-lg-baseline
    .align-self-xl-end
    .row-cols-sm-8
    .row-cols-md-6
    .row-cols-lg-4
    .row-cols-xl-2

    View full-size slide

  49. .d-sm-block
    .d-md-inline-block
    .d-lg-flex
    .d-xl-none

    View full-size slide

  50. .sm:block
    .md:inline-block
    .lg:flex
    .xl:hidden

    View full-size slide

  51. .sm:text-red-500
    .md:text-center
    .lg:text-lg
    .xl:font-bold
    .sm:mt-0
    .md:px-4
    .lg:w-40
    .xl:h-24
    .sm:self-start
    .md:justify-center
    .lg:items-baseline
    .xl:content-around
    .sm:border-2
    .md:border-blue-500
    .lg:border-dashed
    .xl:rounded-full
    .sm:grid-cols-2
    .md:grid-cols-4
    .lg:grid-cols-6
    .xl:grid-cols-8
    .sm:flex-grow
    .md:flex-shrink
    .lg:flex-initial
    .xl:flex-auto
    .sm:bg-gray-100
    .md:bg-fixed
    .lg:bg-opacity-50
    .xl:bg-left
    .sm:transition
    .md:duration-100
    .lg:scale-50
    .xl:translate-100
    .sm:block
    .md:inline-block
    .lg:flex
    .xl:hidden

    View full-size slide

  52. @responsive {
    .hyphens-none {
    hyphens: none;
    }
    .hyphens-manual {
    hyphens: manual;
    }
    .hyphens-auto {
    hyphens: auto;
    }
    }
    PostCSS directive

    View full-size slide

  53. @media (min-width: 640px) {
    .sm\:hyphens-none { hyphens: none; }
    .sm\:hyphens-manual { hyphens: manual; }
    .sm\:hyphens-auto { hyphens: auto; }
    }
    @media (min-width: 768px) {
    .md\:hyphens-none { hyphens: none; }
    .md\:hyphens-manual { hyphens: manual; }
    .md\:hyphens-auto { hyphens: auto; }
    }
    @media (min-width: 1024px) {
    .lg\:hyphens-none { hyphens: none; }
    .lg\:hyphens-manual { hyphens: manual; }
    .lg\:hyphens-auto { hyphens: auto; }
    }
    @media (min-width: 1280px) {
    .xl\:hyphens-none { hyphens: none; }
    .xl\:hyphens-manual { hyphens: manual; }
    .xl\:hyphens-auto { hyphens: auto; }
    }

    View full-size slide

  54. ~1.8MB
    uncompressed
    ~148KB
    minified and compressed with Gzip
    ~44KB
    compressed with Brotli

    View full-size slide

  55. module.exports = {
    purge: [
    'src/**/*.html',
    'src/**/*.vue',
    'src/**/*.jsx',
    ],
    theme: {},
    variants: {},
    plugins: [],
    }
    tailwind.config.js

    View full-size slide

  56. You must list all files in your project that reference
    any of Tailwind class names
    !
    You must not use string concatenation
    to create class names
    !



    View full-size slide

  57. Reducing features
    2

    View full-size slide

  58. module.exports = {
    theme: {
    borderColor: theme => ({ 'green': theme('colors.green.300') }),
    divideColor: theme => ({ 'green': theme('colors.green.300') }),
    translate: { '1': '0.25rem' },
    },
    corePlugins: [
    'placeholderColor', 'placeholderOpacity', 'textOpacity',
    'skew', 'scale', 'rotate', 'gap',
    'gridColumn', 'gridColumnStart', 'gridColumnEnd',
    'gridRow', 'gridRowStart', 'gridRowEnd',
    ].reduce((list, plugin) => ({ [plugin]: false, ...list }), {}),
    variants: {
    textColor: ['hover', 'focus'],
    backgroundColor: ['hover', 'focus'],
    borderRadius: [], borderOpacity: ['hover', 'focus'],
    transitionDuration: [], transitionDelay: [],
    },
    }
    tailwind.config.js

    View full-size slide

  59. 0
    450
    900
    1350
    1800
    Uncompressed Gzip
    Original Reduced
    1800K
    400K
    148KB
    56K

    View full-size slide

  60. Recap
    • maps closely to CSS
    • naming optimized for writing
    • generous defaults (colors, spacing)
    • pseudo-class & responsive variants (for each class)
    • PostCSS directives & functions
    • advanced JavaScript-based configuration

    View full-size slide

  61. Resources
    • https://tailwindcss.com/docs
    • https://tailwindcss.com/screencasts
    • https://tailwindcss-custom-forms.netlify.app/
    • https://marketplace.visualstudio.com/items?itemName=bradlc.vscode-
    tailwindcss
    • https://github.com/aniftyco/awesome-tailwindcss
    • https://adamwathan.me/css-utility-classes-and-separation-of-concerns/
    • Adam Wathan’s YouTube channel
    • Steve Schoger's design tips

    View full-size slide