Tailwind CSSのコンフリクトで反映されないのを防ぐ方法

Tailwind CSSのコンフリクトとは

Tailwind CSSは色のclass名が2つ以上付いているとコンフリクトして反映されないことがあります。

例えば以下のようなclass名「text-blue-500」が付いている要素にJavaScriptで「text-red-500」を追加しても赤色が反映されません。

JavaScript
const h1 = document.querySelector('h1')
const btn = document.querySelector('button')

btn.addEventListener('click', () => {
  h1.classList.add('text-red-500')
})

See the Pen Tailwind CSS Conflict Bad Pattern by iwbjp (@xzdrtugn-the-reactor) on CodePen.

これはTailwind CSSのtext-red-500よりtext-blue-500のほうがあとに書かれているからです。

CSS
.text-red-500 {
  --tw-text-opacity: 1;
  color: rgba(239,68,68,var(--tw-text-opacity))
}

/* 中略 */

.text-blue-500 {
  --tw-text-opacity: 1;
  color: rgba(59,130,246,var(--tw-text-opacity))
}

Tailwind CSSのコンフリクトを防ぐにはいくつか方法があります。

Tailwind CSS IntelliSenseを使う

VS CodeのTailwind CSS IntelliSenseのLinterの機能により、HTMLのclassに「text-blue-500 text-red-500」のような記述があると警告してくれるので、コンフリクトに気づけます。

Tailwind CSS IntelliSense Linter

Tailwind CSS IntelliSense

class名を追加ではなく置換する

text-blue-500にtext-red-500を追加ではなく置換にすればtext-red-500だけが反映されます。

JavaScript
const h1 = document.querySelector('h1')
const btn = document.querySelector('button')

btn.addEventListener('click', () => {
  h1.classList.replace('text-blue-500', 'text-red-500')
})

class名がtext-blue-500のように固定でなければ、こちらの方法は使えません。

See the Pen Tailwind CSS Conflict Good Pattern by iwbjp (@xzdrtugn-the-reactor) on CodePen.

tailwind-mergeを使用する

tailwind-mergeを使用すれば、複数のclass名があっても、最適化されて適用されます。

JavaScript
import { twMerge } from 'tailwind-merge'

twMerge('px-2 py-1 bg-red hover:bg-dark-red', 'p-3 bg-[#B91C1C]')
// → 'hover:bg-dark-red p-3 bg-[#B91C1C]'

tailwind-merge

!importantを使用してはいけない

たまに以下のように!importantを使用されているケースがありますが、!importantは非推奨なので使用しないほうが良いです。

古いTailwind CSSだと!importantだと適用されないというデメリットもあります。

HTML
<h1 class="text-blue-500 !text-red-500">サンプル</h1>
カテゴリーcss