/learn-tailwind

🌬️ Learn Tailwind CSS to craft pixel-perfect web apps/sites in less time! 😍

Primary LanguageElixirGNU General Public License v2.0GPL-2.0

tailwind-css-logo

Learn Tailwind CSS to craft pixel-perfect beautifully adaptive web apps/sites in less time.

GitHub Workflow Status codecov.io npm package version Hex.pm contributions welcome HitCount


Use these links to skip stright to the section that interests you:

Why?

Many people consider CSS difficult.

family-guy-css-meme

Plenty of memes: google.com/search?q=css+meme

We think everyone building web apps/sites should learn CSS.
However we agree that it can feel frustrating and often overwhelming.
Many software engineers/developers feel they already have enough to learn with the rest of their chosen "stack", so investing the time to perfect the interface design & layout feels like too much. We get it!

Learning Tailwind will not mean you don't need to learn/understand CSS. But it will make it a lot easier.

We think the infamy of CSS is unjustified. Like learning how to juggle, you will get hit in the face by a few stray objects in your quest to learn CSS. If you invest the time to learn CSS from first principals, you will have the skills to avoid the frustration. As with most things, it's usually just a matter of making the time to learn/understand it.

Why Switch to Tailwind?

We have not taken the decision to switch our UI library lightly. As with all technology decisions, we must weigh the pros & cons carefully because there is a substantial time investment required.

We felt (still feel) that the benefits of switching (outlined below) justify the cost - learning time, updating code & maintenance.

We encourage you to read through this doc and make up your own mind if Tailwind is a good fit for you and your team/project.

What?

Tailwind CSS is a utility-first CSS framework that can be composed to build any design, directly in your markup. ~ tailwindcss.com

💡 Tip: Read through the Tailwind landing page, it summarises the benefits very well.

In-line styles directly in a UI element so you never have to hunt for a style definition across multiple files. It means you don't suffer the change-one thing breaks many others pain of traditional CSS.

This is a huge time saver even in a modest sized project.

Top 10 Reasons We Love Tailwind

  1. Declarative utility focussed CSS classes that allow you to locally scope all presentation and avoid polluting the global space.
  2. Logical numeric property increments mean it's immediately obvious from reading the class bg-red-500 #ef4444 in your HTML that the background is red and the intensity is 500
    (on the scale 0-1000) and therefore logically the "hover background red 700" hover:bg-red-700 #b91c1c is a deeper red. See: Colors section below.
  3. Flexible function-like class names let you define precise values for attributes like position, padding, margin e.g: m-[5px] or m-[2%] when you need a very specific pixel dimension or a specific percentage. see: tailwindcss.com/docs/margin#arbitrary-values This is a huge improvement over being stuck with pre-defined values! Consider this compound class to create a gradient:
    bg-gradient-to-r from-green-400 to-blue-500
    tailwind-gradient-demo
    Even a complete beginner can infer what these 3 classes are doing:
    "Background gradient to right, from green level 400 #4ade80, to blue level 500 #0ea5e9".

    Note: Obvs we don't do this in practice, but it shows the power! 🌈

  4. Superb visual documentation with easy two-way search; lookup the CSS attirbute or Tailwind class with auto-completion makes finding what you need very fast!
  5. Built-in pre-processor bundles and minimises your styles so you never ship bloated CSS again; especially important for larger projects.
  6. Actively developed by the original author who is working full-time and still passionate about the project, see: What's New in Tailwind v3.1 where the creator Adam Wathan summarises recent improvements.
  7. Thriving community with many contributors and frequent improvements, see: github.com/tailwindlabs/tailwindcss
  8. UI Library [not free but very reasonably priced!] which means there is a sustainable business model i.e: it wont cease to be maintained because the creator is getting paid to do it full-time.
  9. Free complete themes, UI components/kits & resources to kick-start your project. e.g: tailwindtoolbox.com tailwindtoolbox
  10. Please add yours here!! 🙏

!important Tailwind Eliminates the "Cascade"

One of the most amazing and powerful features of CSS ("Cascading Style Sheets") is also one of the greatest sources of frustration when using it in practice. When you have a "cascade", styles can be applied globally to your web site/app and thus you only have to change things in one place for them to take effect everwhere. In practice this only works when everyone editing the CSS is reasonably proficient and there is a clear system for making the changes.

When all styles are globally scoped, making fine adjustments to the position of a particular UI element becomes tedious which leads to spagheti code full of specificity headaches. If you see the word !important in CSS you know that people have given up on the maintainability.

What about Tachyons?

@dwyl we've been using Taychyons (Functional CSS Library) for the past 5 years and (as always) comprehensively documented our learning in dwyl/learn-tachyons and dwyl/tachyons-bootstrap.
Tachyons preceeds Tailwind by 3 years - inital release 2014 vs. 2017 - so you could even say that one inspired or layed the groundwork for the other. We still ❤️ Tachyons and will use it where it makes sense. Tachyons is lightweight (14kb) and has very similar utility classes to Tailwind; we consider the two almost interchangeable. We won't be updating any of the projects that use Tachyons to use Tailwind because none of them are "broken", require zero maintenance and work well as-is!

The key diference is approach taken to building the library. Tachyons is just the CSS (which is great for anywhere you don't want to have build pipeline/process) whereas Tailwind is a JavaScript library that includes parser/pre-processor.

The advantage of having a JS library means you can create your own Functions, Components and Directives that are immensely powerful and offer significant flexibility.

JS means you are forced to have a build step in your dev/deployment pipeline to use Tailwind. However, given that Tailwind works with esbuild (which is very fast and reliable and already included with Phoenix) we feel that the trade-off is worth it.

With Tailwind we get the "best of both worlds", we get a utility-first CSS library, that also has the flexibility/power of a customizable design system.

What about XYZ Framework?

There is a virtually endless list of CSS frameworks, component libraries and pre-processors available.
see: github.com/troxler/awesome-css-frameworks ...
For a good comparison read: athemes.com/collections/best-css-frameworks or dev.to/samlan/best-css-frameworks-for-2022-1afm

Ultimately for us, we did our own research into the available alternatives but kept an open mind. We were guided by the Elixir / Phoenix community toward Tailwind and we have not been disapointed.

Tailwind in Phoenix

As of Phoenix 1.7, Tailwind is now included by default. We called it last year. And we're delighted our investment payed off!


Who?

This guide is aimed at anyone that:

A. Wants to evaluate Tailwind for themselves or their team without the hype/noise.
B. Needs to learn Tailwind as fast as possible but without skipping any steps!
C. Has to summarise & share their knowledge of Tailwind with a team/community of people.

If you find this useful, please ⭐ on GitHub to let us and others know. Thanks! 🙏

How?

If you just want to test Tailwind with the least effort, use the online playground: play.tailwindcss.com

tailwind-play-color-change

Speed-read through the docs: tailwindcss.com/docs/utility-first and try a changing a few values, e.g: start by changing solors names/levels.

Part 1: Try Before You Commit

The official get started guide instructs you to perform several setup (installation) steps before you try the framework. But you can skip these steps if you just want to evaluate it.

Create index.html

Create an index.html file on your computer with the following contents: https://raw.githubusercontent.com/tailwindtoolbox/Admin-Template/master/index.html

Open the file in your web brower, you should see something similar to:

admin-dashboard-example

Once you've made a few changes in the index.html file and seen the results in your web browser, you should have a decent idea of the power of Tailwind.

If you have a decent Internet connection and no bandwidth constraints, we recommend watching Designing with Tailwind CSS: The Utility-First Workflow: https://youtu.be/Ybybd3GCNn4

Designing with Tailwind CSS

made by Adam Wathan @adamwathan (Creator of Tailwind)

Colors!

We are huge fans of the numeric indexing of the built-in colors: https://tailwindcss.com/docs/customizing-colors tailwind-colors


Part 2: Tailwind in Phoenix

To run the finished version of our Tailwind + Phoenix Demo, run:

git clone git@github.com:dwyl/learn-tailwind.git && cd learn-tailwind
mix setup
mix phx.server

Build Log (How we got here)

Create a barebones Phoenix App:

mix phx.new app --no-mailer --no-dashboard --no-gettext --no-ecto

Install the dependencies. Then open the project in your editor.

Run the app:

mix phx.server

You should see output similar to the following in your terminal:

Generated app app
[info] Running AppWeb.Endpoint with cowboy 2.9.0 at 127.0.0.1:4000 (http)
[info] Access AppWeb.Endpoint at http://localhost:4000
[debug] Downloading esbuild from https://registry.npmjs.org/esbuild-darwin-64/-/esbuild-darwin-64-0.14.29.tgz
[watch] build finished, watching for changes...

That's a good sign, esbuild was downloaded and the assets were compiled successfully.

Visit localhost:4000 from your browser.

You should see something similar to the following (default Phoenix homepage):

phoenix-default-homepage

That's nice. But a bit boring ... let's add some pizzazz! ✨

Open the mix.exs file and add :tailwind to defp deps:

{:tailwind, "~> 0.1.9", runtime: Mix.env() == :dev},

Run:

mix deps.get

Once installed, add the following lines to config/config.exs to pick your tailwind version of choice:

config :tailwind,
  version: "3.1.0",
  default: [
    args: ~w(
      --config=tailwind.config.js
      --input=css/app.css
      --output=../priv/static/assets/app.css
    ),
    cd: Path.expand("../assets", __DIR__)
  ]

Now you can install the library. Run the following commands in order.

mix tailwind.install
mix tailwind default

These commands will generate the Tailwind CLI and create a assets/tailwind.config.js file. They will also create an executable inside _build/tailwind-TARGET where TARGET is your target system architecture.

For development, we want to enable watch mode. So find the watchers section in config/dev.exs and add:

tailwind: {Tailwind, :install_and_run, [:default, ~w(--watch)]}

Note: this enables the file system watcher.

Ensure that the import "../css/app.css" line is no longer in assets/js/app.js (should have automatically been removed by adding Tailwind ...)

Finally, back in your mix.exs, make sure you have a assets.deploy alias for deployments, which will also use the --minify option:

"assets.deploy": ["tailwind default --minify", "esbuild default --minify", "phx.digest"]

Open the lib/app_web/templates/page/index.html.heex and replace the contents with:

<h1
  class="text-7xl text-white font-bold text-center w-full bg-slate-800 rounded-xl shadow-lg py-3 mt-3 ml-3"
>
  Hello TailWorld!
</h1>

Run the Phoenix App:

mix phx.server

Visit localhost:4000 in your web browser:

image

Those semantic utility class names should give you a flavour for what to expect in the UI.

Fix the failing tests!

Open test/app_web/controllers/page_controller_test.exs and change the assertion from:

assert html_response(conn, 200) =~ "Welcome to Phoenix!"

to:

assert html_response(conn, 200) =~ "Hello TailWorld!"

More Detailed Example!

We're using Tailwind for our Phoenix LiveView Chat Example: https://github.com/dwyl/phoenix-liveview-chat-example

liveview-chat-with-tailwind-css

We think it's siiiiiiick! More examples to follow soon!

Petal Components

petal.build

Petal components are a set of reusable functions to help you build a nice UI:

image

Follow the instructions steps at https://petal.build/components to install the Petal components to your Phoenix project. After that you'll be able to call in your templates the components with the syntax <.component>...</.component>, for example:

<.h2>Title</.h2>

see: