Răsfoiți Sursa

feat(ui-devkit): Support Clarity Sass variable overrides (#1684)

Vinicius Rosa 3 ani în urmă
părinte
comite
46d1e2d3a3

+ 35 - 3
docs/content/plugins/extending-the-admin-ui/admin-ui-theming-branding/_index.md

@@ -65,7 +65,7 @@ You can replace the Vendure logos and favicon with your own brand logo:
 
 ## Theming
 
-Much of the visual styling of the Admin UI can be customized by providing your own themes in a Sass stylesheet. The Admin UI uses [CSS custom properties](https://developer.mozilla.org/en-US/docs/Web/CSS/--*) to control colors and other styles. Here's a simple example which changes the color of links:
+Much of the visual styling of the Admin UI can be customized by providing your own themes in a Sass stylesheet. For the most part, the Admin UI uses [CSS custom properties](https://developer.mozilla.org/en-US/docs/Web/CSS/--*) to control colors and other styles. Here's a simple example which changes the color of links:
 
 1. Install `@vendure/ui-devkit`
 2. Create a custom stylesheet which overrides one or more of the CSS custom properties used in the Admin UI:
@@ -78,13 +78,13 @@ Much of the visual styling of the Admin UI can be customized by providing your o
       --clr-link-visited-color: hsl(110, 55%, 75%);
     }
     ```
-   To get an idea of which custom properties are avaiable for theming, take a look at the source of the [Default theme](https://github.com/vendure-ecommerce/vendure/tree/master/packages/admin-ui/src/lib/static/styles/theme/default.scss) and the [Dark theme](https://github.com/vendure-ecommerce/vendure/tree/master/packages/admin-ui/src/lib/static/styles/theme/dark.scss)
+   To get an idea of which custom properties are available for theming, take a look at the source of the [Default theme](https://github.com/vendure-ecommerce/vendure/tree/master/packages/admin-ui/src/lib/static/styles/theme/default.scss) and the [Dark theme](https://github.com/vendure-ecommerce/vendure/tree/master/packages/admin-ui/src/lib/static/styles/theme/dark.scss)
 3. Set this as a globalStyles extension:   
     ```TypeScript
     import path from 'path';
     import { AdminUiPlugin } from '@vendure/admin-ui-plugin';
     import { VendureConfig } from '@vendure/core';
-    import { compileUiExtensions, setBranding } from '@vendure/ui-devkit/compiler';
+    import { compileUiExtensions } from '@vendure/ui-devkit/compiler';
     
     export const config: VendureConfig = {
       // ...
@@ -100,3 +100,35 @@ Much of the visual styling of the Admin UI can be customized by providing your o
       ],
     }
     ```
+
+Some customizable styles in [Clarity](https://clarity.design/), Admin UI's Design System framework, are controlled by Sass variables, which can be found on the [project's GitHub page](https://github.com/vmware-clarity/ng-clarity/blob/689a572344149aea90df1676eae04479795754f3/projects/angular/src/utils/_variables.clarity.scss). Similar to above, you can also provide your own values, which will override defaults set by the framework. Here's an example which changes the [height of the main header](https://github.com/vmware-clarity/ng-clarity/blob/689a572344149aea90df1676eae04479795754f3/projects/angular/src/layout/main-container/_variables.header.scss#L10):
+
+1. Install `@vendure/ui-devkit` if not already installed
+2. Create a custom stylesheet which overrides the target variable(s):
+    ```css
+    /* my-variables.scss */
+    $clr-header-height: 4rem;
+    ```
+3. Set this as a sassVariableOverrides extension:
+    ```TypeScript
+    import path from 'path';
+    import { AdminUiPlugin } from '@vendure/admin-ui-plugin';
+    import { VendureConfig } from '@vendure/core';
+    import { compileUiExtensions } from '@vendure/ui-devkit/compiler';
+
+    export const config: VendureConfig = {
+      // ...
+      plugins: [
+        AdminUiPlugin.init({
+          app: compileUiExtensions({
+            outputPath: path.join(__dirname, 'admin-ui'),
+            extensions: [{
+              sassVariableOverrides: path.join(__dirname, 'my-variables.scss')
+            }],
+          }),
+        }),
+      ],
+    }
+    ```
+
+globalStyles and sassVariableOverrides extensions can be used in conjunction or separately.

+ 2 - 2
packages/admin-ui/README.md

@@ -4,13 +4,13 @@ This is the administration interface for Vendure.
 
 It is an Angular application built with the Angular CLI.
 
-The UI is powered by the [Clarity Design System](https://vmware.github.io/clarity/).
+The UI is powered by the [Clarity Design System](https://clarity.design).
 
 ## Structure
 
 ### Library
 
-The Admin UI is structured as an Angular library conforming to the [ng-packagr format](https://github.com/ng-packagr/ng-packagr). This library is what is published to npm as `@vendure/admin-ui`. The libary consists
+The Admin UI is structured as an Angular library conforming to the [ng-packagr format](https://github.com/ng-packagr/ng-packagr). This library is what is published to npm as `@vendure/admin-ui`. The library consists
 of a set of modules which are accessible from consuming applications as sub-packages:
 
 * `@vendure/admin-ui/core`

+ 2 - 2
packages/admin-ui/scripts/compile-styles.js

@@ -15,7 +15,7 @@ const result = sass.renderSync({
 
 fs.writeFileSync(outFile, result.css, 'utf8');
 
-function importer(url, prev, done) {
+function importer(url, prev) {
     let file = url;
     // Handle the imports prefixed with ~
     // which are usually resolved by Webpack.
@@ -29,7 +29,7 @@ function importer(url, prev, done) {
     // library styles which are not needed in external
     // apps.
     if (/^~@(ng-select|angular)/.test(url)) {
-        return false;
+        return null;
     }
 
     return { file };

+ 1 - 1
packages/admin-ui/src/lib/core/src/components/app-shell/app-shell.component.scss

@@ -14,7 +14,7 @@
 }
 vdr-breadcrumb {
     @media screen and (min-width: $breakpoint-small){
-        margin-left: 10.8rem;
+        margin-left: $clr-sidenav-width;
     }
 }
 .header-actions {

+ 0 - 1
packages/admin-ui/src/lib/core/src/components/main-nav/main-nav.component.scss

@@ -8,7 +8,6 @@
 
 nav.sidenav {
     height: 100%;
-    width: 10.8rem;
     border-right-color: var(--clr-sidenav-border-color);
 }
 

+ 3 - 0
packages/admin-ui/src/lib/static/styles/_variables.scss

@@ -1,2 +1,5 @@
+@import "~@clr/ui/src/utils/_mixins";
+@import "~@clr/ui/src/utils/_variables.clarity.scss";
+
 // breakpoints
 $breakpoint-small: 768px;

+ 3 - 0
packages/admin-ui/src/lib/static/styles/global/_sass-overrides.scss

@@ -0,0 +1,3 @@
+// Note: variables defined in this file should use the default! flag so they can be
+// overridden by custom Admin UI applications
+$clr-sidenav-width: 10.8rem !default;

+ 1 - 0
packages/admin-ui/src/lib/static/styles/styles.scss

@@ -1,3 +1,4 @@
+@import "global/sass-overrides";
 @import "~@clr/icons/clr-icons.min.css";
 @import "~@clr/ui/src/utils/components.clarity";
 @import "~@ng-select/ng-select/themes/default.theme.css";

+ 1 - 0
packages/admin-ui/src/lib/static/styles/ui-extension-theme.scss

@@ -1,6 +1,7 @@
 // This file is used to compile the theme.min.css file which can be used
 // by ui extensions to get the same styles as the main app.
 
+@import "global/sass-overrides";
 // Clarity Component SCSS
 @import "~@clr/ui/src/main";
 @import "global/overrides";

+ 23 - 3
packages/ui-devkit/src/compiler/scaffold.ts

@@ -17,6 +17,7 @@ import {
     AdminUiExtensionSharedModule,
     Extension,
     GlobalStylesExtension,
+    SassVariableOverridesExtension,
     StaticAssetExtension,
 } from './types';
 import {
@@ -24,6 +25,7 @@ import {
     copyUiDevkit,
     isAdminUiExtension,
     isGlobalStylesExtension,
+    isSassVariableOverridesExtension,
     isStaticAssetExtension,
     isTranslationExtension,
     logger,
@@ -43,7 +45,8 @@ export async function setupScaffold(outputPath: string, extensions: Extension[])
     await copyStaticAssets(outputPath, staticAssetExtensions);
 
     const globalStyleExtensions = extensions.filter(isGlobalStylesExtension);
-    await addGlobalStyles(outputPath, globalStyleExtensions);
+    const sassVariableOverridesExtension = extensions.find(isSassVariableOverridesExtension);
+    await addGlobalStyles(outputPath, globalStyleExtensions, sassVariableOverridesExtension);
 
     const allTranslationFiles = getAllTranslationFiles(extensions.filter(isTranslationExtension));
     await mergeExtensionTranslations(outputPath, allTranslationFiles);
@@ -93,12 +96,17 @@ async function copyStaticAssets(outputPath: string, extensions: Array<Partial<St
     }
 }
 
-async function addGlobalStyles(outputPath: string, extensions: GlobalStylesExtension[]) {
+async function addGlobalStyles(
+    outputPath: string,
+    globalStylesExtensions: GlobalStylesExtension[],
+    sassVariableOverridesExtension?: SassVariableOverridesExtension,
+) {
     const globalStylesDir = path.join(outputPath, 'src', GLOBAL_STYLES_OUTPUT_DIR);
     await fs.remove(globalStylesDir);
     await fs.ensureDir(globalStylesDir);
+
     const imports: string[] = [];
-    for (const extension of extensions) {
+    for (const extension of globalStylesExtensions) {
         const styleFiles = Array.isArray(extension.globalStyles)
             ? extension.globalStyles
             : [extension.globalStyles];
@@ -107,7 +115,19 @@ async function addGlobalStyles(outputPath: string, extensions: GlobalStylesExten
             imports.push(path.basename(styleFile, path.extname(styleFile)));
         }
     }
+
+    let overridesImport = '';
+    if (sassVariableOverridesExtension) {
+        const overridesFile = sassVariableOverridesExtension.sassVariableOverrides;
+        await copyGlobalStyleFile(outputPath, overridesFile);
+        overridesImport = `@import "./${GLOBAL_STYLES_OUTPUT_DIR}/${path.basename(
+            overridesFile,
+            path.extname(overridesFile),
+        )}";\n`;
+    }
+
     const globalStylesSource =
+        overridesImport +
         `@import "./styles/styles";\n` +
         imports.map(file => `@import "./${GLOBAL_STYLES_OUTPUT_DIR}/${file}";`).join('\n');
 

+ 25 - 8
packages/ui-devkit/src/compiler/types.ts

@@ -4,7 +4,8 @@ export type Extension =
     | AdminUiExtension
     | TranslationExtension
     | StaticAssetExtension
-    | GlobalStylesExtension;
+    | GlobalStylesExtension
+    | SassVariableOverridesExtension;
 
 /**
  * @description
@@ -65,6 +66,22 @@ export interface GlobalStylesExtension {
     globalStyles: string[] | string;
 }
 
+/**
+ * @description
+ * Defines an extension which allows overriding Clarity Design System's Sass variables used in styles on the Admin UI.
+ *
+ * @docsCategory UiDevkit
+ * @docsPage AdminUiExtension
+ */
+export interface SassVariableOverridesExtension {
+    /**
+     * @description
+     * Specifies a path to a Sass style file containing variable declarations, which will take precedence over
+     * default values defined in Clarity.
+     */
+    sassVariableOverrides: string;
+}
+
 /**
  * @description
  * Defines extensions to the Admin UI application by specifying additional
@@ -176,10 +193,10 @@ export interface AdminUiExtensionLazyModule {
 /**
  * @description
  * Argument to configure process (watch or compile)
- * 
+ *
  * @docsCategory UiDevkit
  */
-export type UiExtensionCompilerProcessArgument = string | [string, any]
+export type UiExtensionCompilerProcessArgument = string | [string, any];
 
 /**
  * @description
@@ -226,7 +243,7 @@ export interface UiExtensionCompilerOptions {
      * @default 4200 | undefined
      */
     watchPort?: number;
-    
+
     /**
      * @description
      * Internally, the Angular CLI will be invoked as an npm script. By default, the compiler will use Yarn
@@ -239,14 +256,14 @@ export interface UiExtensionCompilerOptions {
 
     /**
      * @description
-     * Additional command-line arguments which will get passed to the [ng build](https://angular.io/cli/build) 
+     * Additional command-line arguments which will get passed to the [ng build](https://angular.io/cli/build)
      * command (or [ng serve](https://angular.io/cli/serve) if `devMode = true`).
-     * 
+     *
      * @example
      * ['--disable-host-check'] // to disable host check
-     * 
+     *
      * @default undefined
-     * 
+     *
      * @since 1.5.0
      */
     additionalProcessArguments?: UiExtensionCompilerProcessArgument[];

+ 5 - 0
packages/ui-devkit/src/compiler/utils.ts

@@ -10,6 +10,7 @@ import {
     AdminUiExtension,
     Extension,
     GlobalStylesExtension,
+    SassVariableOverridesExtension,
     StaticAssetDefinition,
     StaticAssetExtension,
     TranslationExtension,
@@ -106,3 +107,7 @@ export function isStaticAssetExtension(input: Extension): input is StaticAssetEx
 export function isGlobalStylesExtension(input: Extension): input is GlobalStylesExtension {
     return input.hasOwnProperty('globalStyles');
 }
+
+export function isSassVariableOverridesExtension(input: Extension): input is SassVariableOverridesExtension {
+    return input.hasOwnProperty('sassVariableOverrides');
+}