Drupal Theme With Vite And UnoCSS In Lando

UnoCSS is a tailwind-like framework. Vite is used to compile and serve assets.

This page is a guide for setting it up in lando with hot reloading.

 

.lando.yml

name: demo
recipe: drupal10
config:
  webroot: web
proxy:
  node:
    - node.demo.lndo.site:3000
services:
  node:
    type: node:18
    ssl: true
    sslExpose: false
    port: 3000
    scanner: false
tooling:
  npm:
    service: node
    cmd: npm

ssl: true and sslExpose: false create certs but don't expose the url.

scanner: false prevents lando's link scanner from waiting for the url to load (as it's launched later if needed).

port: 3000 sets the service to use port 3000, which the proxy will respond to.

 

Create a theme and install unocss/vite:

drush gen theme

Move the css directory into src/css.

npm init
npm i -D unocss

More info: https://unocss.dev/integrations/vite

 

vite.config.js

import UnoCSS from 'unocss/vite'
import { defineConfig } from 'vite'
import liveReload from 'vite-plugin-live-reload'

export default(({mode}) => {
  return defineConfig({
    plugins: [
      UnoCSS(),
      liveReload(__dirname + '/**/*.(php|theme|twig|module)'),
    ],

    // Handle base path for dev/build.
    base: mode === 'development' ? '/' : '/themes/demo_theme/src',

    build: {
      // Clear out dist directory on build.
      emptyOutDir: true,

      // Create manifest to map library src to dist output.
      manifest: true,

      // JS sourcemaps.
      sourcemap: true,

      rollupOptions: {
        // plugins: [nodeResolve()],
        input: './src/main.js'
      },
    },
    
    // CSS is printed inline in js modules,
    // enabling devSourcemap lets it be viewed as a file in the inspector.
    css: { devSourcemap: true },

    server: {
      // SSL is handled by the lando proxy.
      https: false,
      // Listen for connections.
      host: true,
      // Set fixed port 3000.
      port: 3001,
      // origin: 'https://node.demo.lndo.site',
      // proxy: {
      //   '/@unocss-devtools-update':
      // },
      // Configure hmr.
      hmr: {host: 'node.demo.lndo.site', protocol: 'wss'}
    },
  })
})

 

uno.config.js

import {
  defineConfig, presetAttributify, presetIcons,
  presetTypography, presetUno, presetWebFonts,
  transformerDirectives, transformerVariantGroup
} from 'unocss'

export default defineConfig({
  shortcuts: [],
  theme: {
    colors: {
      green: '#0F0',
    }
  },

  rules: [
    [/^text-(.*)$/, ([, c], { theme }) => {
      if (theme.colors[c])
        return { color: theme.colors[c] }
    }],
  ],

  presets: [
    presetUno(),
    presetAttributify(),
    presetIcons(),
    presetTypography(),
    presetWebFonts({
      fonts: {},
    }),
  ],

  transformers: [
    transformerDirectives(),
    transformerVariantGroup(),
  ],
})

 

demo_theme.libraries.yml

global:
  vite: true
  js:
    src/main.js: {}
    //cdn.jsdelivr.net/npm/@unocss/runtime:
      type: external
      minified: true
  css:
    base:
      src/main.css: {}

 

main.js

import 'uno.css'
import './main.css'

 

Development

The assets can be built for production with npm run build.

Using npm run dev will run vite as a server for hot reloading. The uno runtime can be loaded in the browser so modifying html classes in the inspector will load new styles.

We should be able to include the vite runtime from the development server, but I haven't gotten it to work yet. Including 'virtual:uno.css' in main.js should bundle it, but when it's loaded in the Drupal site, the callback urls for requesting styles goes to drupal instead of vite. Using server.origin: 'https://node.demo.lndo.site' will fix the urls, but then a CORS error appears. See: https://github.com/unocss/unocss/issues/3043

As a workaround, edit @unocss/vite/dist/client.mjs and add mode: no-cors to the post function.

Alternatively, load the runtime library as a theme asset according to https://unocss.dev/integrations/runtime

You will need to ensure certs are working for your system: https://docs.lando.dev/core/v3/security.html#trusting-the-ca.

To get sourcemaps to work in firefox, I had to set "Show Original Sources" in the style editor settings.

Image
Firefox style editor settings
Tags
Modules