From 55ba270b833b389c27b6818f7919da366724ebda Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 10:51:49 -0400 Subject: [PATCH 01/11] add support for fixed width --- src/components/icon/icon.styles.ts | 4 + src/components/icon/icon.ts | 127 +++++++++++++++-------------- 2 files changed, 69 insertions(+), 62 deletions(-) diff --git a/src/components/icon/icon.styles.ts b/src/components/icon/icon.styles.ts index 6b459f375..179103e8f 100644 --- a/src/components/icon/icon.styles.ts +++ b/src/components/icon/icon.styles.ts @@ -8,6 +8,10 @@ export default css` box-sizing: content-box !important; } + :host[fixed-width] { + width: 1em; + } + svg { display: block; height: 100%; diff --git a/src/components/icon/icon.ts b/src/components/icon/icon.ts index 8faf5dc08..f5a738bbf 100644 --- a/src/components/icon/icon.ts +++ b/src/components/icon/icon.ts @@ -41,6 +41,71 @@ export default class WaIcon extends WebAwesomeElement { private initialRender = false; + @state() private svg: SVGElement | HTMLTemplateResult | null = null; + + /** The name of the icon to draw. Available names depend on the icon library being used. */ + @property({ reflect: true }) name?: string; + + /** + * The family of icons to choose from. For Font Awesome, valid options include `classic`, `sharp`, `duotone`, and + * `brands`. Custom icon libraries may or may not use this property. + */ + @property({ reflect: true }) family: string; + + /** + * The name of the icon's variant. For Font Awesome, valid options include `thin`, `light`, `regular`, and `solid` for + * the _classic_ and _sharp_ families. Custom icon libraries may or may not use this property. + */ + @property({ reflect: true }) variant: string; + + /** Draws the icon in a fixed-width both. */ + @property({ attribute: 'fixed-width', type: Boolean, reflect: true }) fixedWidth: false; + + /** + * An external URL of an SVG file. Be sure you trust the content you are including, as it will be executed as code and + * can result in XSS attacks. + */ + @property() src?: string; + + /** + * An alternate description to use for assistive devices. If omitted, the icon will be considered presentational and + * ignored by assistive devices. + */ + @property() label = ''; + + /** The name of a registered custom icon library. */ + @property({ reflect: true }) library = 'default'; + + connectedCallback() { + super.connectedCallback(); + watchIcon(this); + } + + firstUpdated() { + this.initialRender = true; + this.setIcon(); + } + + disconnectedCallback() { + super.disconnectedCallback(); + unwatchIcon(this); + } + + private getIconSource(): IconSource { + const library = getIconLibrary(this.library); + if (this.name && library) { + return { + url: library.resolver(this.name, this.family, this.variant), + fromLibrary: true + }; + } + + return { + url: this.src, + fromLibrary: false + }; + } + /** Given a URL, this function returns the resulting SVG element or an appropriate error symbol. */ private async resolveIcon(url: string, library?: IconLibrary): Promise { let fileData: Response; @@ -90,68 +155,6 @@ export default class WaIcon extends WebAwesomeElement { } } - @state() private svg: SVGElement | HTMLTemplateResult | null = null; - - /** The name of the icon to draw. Available names depend on the icon library being used. */ - @property({ reflect: true }) name?: string; - - /** - * The family of icons to choose from. For Font Awesome, valid options include `classic`, `sharp`, `duotone`, and - * `brands`. Custom icon libraries may or may not use this property. - */ - @property({ reflect: true }) family: string; - - /** - * The name of the icon's variant. For Font Awesome, valid options include `thin`, `light`, `regular`, and `solid` for - * the _classic_ and _sharp_ families. Custom icon libraries may or may not use this property. - */ - @property({ reflect: true }) variant: string; - - /** - * An external URL of an SVG file. Be sure you trust the content you are including, as it will be executed as code and - * can result in XSS attacks. - */ - @property() src?: string; - - /** - * An alternate description to use for assistive devices. If omitted, the icon will be considered presentational and - * ignored by assistive devices. - */ - @property() label = ''; - - /** The name of a registered custom icon library. */ - @property({ reflect: true }) library = 'default'; - - connectedCallback() { - super.connectedCallback(); - watchIcon(this); - } - - firstUpdated() { - this.initialRender = true; - this.setIcon(); - } - - disconnectedCallback() { - super.disconnectedCallback(); - unwatchIcon(this); - } - - private getIconSource(): IconSource { - const library = getIconLibrary(this.library); - if (this.name && library) { - return { - url: library.resolver(this.name, this.family, this.variant), - fromLibrary: true - }; - } - - return { - url: this.src, - fromLibrary: false - }; - } - @watch('label') handleLabelChange() { const hasLabel = typeof this.label === 'string' && this.label.length > 0; From d0b673c99db9f9a097186405c97ecbb929a4529d Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 11:21:17 -0400 Subject: [PATCH 02/11] remove old sprite entry --- .gitignore | 1 - 1 file changed, 1 deletion(-) diff --git a/.gitignore b/.gitignore index b0a6ab872..aa943f40d 100644 --- a/.gitignore +++ b/.gitignore @@ -4,7 +4,6 @@ _site package.json package-lock.json dist -docs/assets/images/sprite.svg docs/public/pagefind node_modules src/react From a134b1a35908f1a866a682bbf3d66b8912355f2f Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 11:21:28 -0400 Subject: [PATCH 03/11] fix examples and remove ::danger --- docs/docs/components/icon.md | 85 ++++++----------------------- docs/docs/resources/contributing.md | 4 -- 2 files changed, 17 insertions(+), 72 deletions(-) diff --git a/docs/docs/components/icon.md b/docs/docs/components/icon.md index 657ba8017..8e1b71d0c 100644 --- a/docs/docs/components/icon.md +++ b/docs/docs/components/icon.md @@ -187,7 +187,7 @@ Here's an example that registers an icon library located in the `/assets/icons` ```html ``` -### Font Awesome - -This will register the [Font Awesome Free](https://fontawesome.com/) library using the jsDelivr CDN. This library has three variations: regular (`far-*`), solid (`fas-*`), and brands (`fab-*`). A mutator function is required to set the SVG's `fill` to `currentColor`. - -Icons in this library are licensed under the [Font Awesome Free License](https://github.com/FortAwesome/Font-Awesome/blob/master/LICENSE.txt). Some of the icons that appear on the Font Awesome website require a license and are therefore not available in the CDN. - -```html {.example} - - -
- - - - - - -
- - - - - - -
- - - - - - -
-``` - ### Heroicons This will register the [Heroicons](https://heroicons.com/) library using the jsDelivr CDN. @@ -331,7 +285,7 @@ Icons in this library are licensed under the [MIT License](https://github.com/ta ```html {.example} - -
- - -
``` ### Customizing the System Library @@ -654,7 +603,7 @@ If you want to change the icons Web Awesome uses internally, you can register an ```html + - ``` @@ -116,7 +115,7 @@ Most of the magic behind assets is handled internally by Web Awesome, but if you ```html ``` +## Setting a Kit Code + +Font Awesome users can set their kit code to unlock Font Awesome Pro icons. You can provide it through the `data-fa-kit-code` attribute or by calling the `setKitCode()` method. + +```html + + + + + +``` + ## Cherry Picking Cherry picking can be done from [the CDN](#cdn-installation-easiest) or from [npm](#npm-installation). This approach will load only the components you need up front, while limiting the number of files the browser has to download. The disadvantage is that you need to import each individual component. @@ -137,10 +151,10 @@ Cherry picking can be done from [the CDN](#cdn-installation-easiest) or from [np Here's an example that loads only the button component. Again, if you're not using a module resolver, you'll need to adjust the path to point to the folder Web Awesome is in. ```html - + - @@ -170,15 +184,15 @@ Now it's time to configure your bundler. Configurations vary for each tool, but Once your bundler is configured, you'll be able to import Web Awesome components and utilities. ```js -import '@shoelace-style/webawesome/%NPMDIR%/themes/default.css'; -import '@shoelace-style/webawesome/%NPMDIR%/components/button/button.js'; -import '@shoelace-style/webawesome/%NPMDIR%/components/icon/icon.js'; -import '@shoelace-style/webawesome/%NPMDIR%/components/input/input.js'; -import '@shoelace-style/webawesome/%NPMDIR%/components/rating/rating.js'; -import { setBasePath } from '@shoelace-style/webawesome/%NPMDIR%/utilities/base-path.js'; +import '/path/to/web-awesome/%NPMDIR%/themes/default.css'; +import '/path/to/web-awesome/%NPMDIR%/components/button/button.js'; +import '/path/to/web-awesome/%NPMDIR%/components/icon/icon.js'; +import '/path/to/web-awesome/%NPMDIR%/components/input/input.js'; +import '/path/to/web-awesome/%NPMDIR%/components/rating/rating.js'; +import { setBasePath } from '/path/to/web-awesome/%NPMDIR%/webawesome.js'; // Set the base path to the folder you copied Web Awesome's assets to -setBasePath('/path/to/webawesome/%NPMDIR%'); +setBasePath('/path/to/web-awesome/%NPMDIR%'); // , , , and are ready to use! ``` @@ -189,7 +203,7 @@ You'll notice that the CDN links all start with `/%CDNDIR%/` and npm impor TL;DR: -- `@shoelace-style/webawesome/%CDNDIR%` is for CDN users -- `@shoelace-style/webawesome/%NPMDIR%` is for npm users +- `/path/to/web-awesome/%CDNDIR%` is for CDN users +- `/path/to/web-awesome/%NPMDIR%` is for npm users This change was introduced in `v2.5.0` to address issues around installations from npm loading multiple versions of libraries (such as the Lit) that Web Awesome uses internally. From 2157b209a269c95dd01ba314c090f164c5f23fb6 Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 14:37:59 -0400 Subject: [PATCH 08/11] update to FA --- docs/docs/components/icon.md | 85 +++++++++++++++++++++++------------- 1 file changed, 55 insertions(+), 30 deletions(-) diff --git a/docs/docs/components/icon.md b/docs/docs/components/icon.md index 59ebf26ce..f2ce74578 100644 --- a/docs/docs/components/icon.md +++ b/docs/docs/components/icon.md @@ -4,24 +4,37 @@ description: Icons are symbols that can be used to represent various options wit layout: component.njk --- -Web Awesome comes bundled with over 1,500 icons courtesy of the [Bootstrap Icons](https://icons.getbootstrap.com/) project. These icons are part of the `default` icon library. If you prefer, you can register [custom icon libraries](#icon-libraries) as well. +Web Awesome comes bundled with over 2,000 free icons courtesy of [Font Awesome](https://fontawesome.com/). These icons are part of the `default` icon library. Font Awesome Pro users can unlock additional icon families. Or, if you prefer, you can register your own [custom icon library](#icon-library). :::info -Depending on how you're loading Web Awesome, you may need to copy icon assets and/or [set the base path](/getting-started/installation/#setting-the-base-path) so Web Awesome knows where to load them from. Otherwise, icons may not appear and you'll see 404 Not Found errors in the dev console. +Not sure which icon to use? [Find the perfect icon over at Font Awesome!](https://fontawesome.com/search?o=r&m=free&f=brands%2Cclassic) ::: -## Default Icons - -All available icons in the `default` icon library are shown below. Click or tap on any icon to copy its name, then you can use it in your HTML like this. - -```html - -``` - ## Examples -TODO - show how to use `family` and `variant` attributes. -TODO - show how to use FA pro via `data-webawesome-kit="..."` +### Families & Variants + +The default icon library is Font Awesome Free, which comes with two icon families: `classic` and `brands`. Use the `family` attribute to set the icon family. + +Many Font Awesome Pro icon families have variants such as `thin`, `light`, `regular`, and `solid`. Font Awesome Pro users can [provide their kit code](/docs/installation) to unlock additional families, including `sharp` and `duotone`. For these icon families, use the `variant` attribute to set the variant. + +```html {.example} + + +``` + +{% raw %} +```jsx {.react} +import WaIcon from '@shoelace-style/shoelace/dist/react/icon'; + +const App = () => ( + <> + + + +); +``` +{% endraw %} ### Colors @@ -95,22 +108,12 @@ Icons are sized relative to the current font size. To change their size, set the ```html {.example}
- - - - - - - - - -
``` @@ -192,14 +195,14 @@ const App = () => ; Custom icons can be loaded individually with the `src` attribute. Only SVGs on a local or CORS-enabled endpoint are supported. If you're using more than one custom icon, it might make sense to register a [custom icon library](#icon-libraries). ```html {.example} - + ``` {% raw %} ```jsx {.react} import WaIcon from '@shoelace-style/shoelace/dist/react/icon'; -const App = () => ; +const App = () => ; ``` {% endraw %} @@ -207,9 +210,9 @@ const App = () => ` component through icon libraries. Icon files can exist locally or on a CORS-enabled endpoint (e.g. a CDN). There is no limit to how many icon libraries you can register and there is no cost associated with registering them, as individual icons are only requested when they're used. -Web Awesome ships with two built-in icon libraries, `default` and `system`. The [default icon library](#customizing-the-default-library) contains all of the icons in the Bootstrap Icons project. The [system icon library](#customizing-the-system-library) contains only a small subset of icons that are used internally by Web Awesome components. +Web Awesome ships with two built-in icon libraries, `default` and `system`. The [default icon library](#customizing-the-default-library) is provided courtesy of [Font Awesome](https://fontawesome.com/). The [system icon library](#customizing-the-system-library) contains only a small subset of icons that are used internally by Web Awesome components. -To register an additional icon library, use the `registerIconLibrary()` function that's exported from `utilities/icon-library.js`. At a minimum, you must provide a name and a resolver function. The resolver function translates an icon name to a URL where the corresponding SVG file exists. Refer to the examples below to better understand how it works. +To register an additional icon library, use the `registerIconLibrary()` function that's exported from `dist/webawesome.js`. At a minimum, you must provide a name and a resolver function. The resolver function translates an icon name to a URL where the corresponding SVG file exists. Refer to the examples below to better understand how it works. If necessary, a mutator function can be used to mutate the SVG element before rendering. This is necessary for some libraries due to the many possible ways SVGs are crafted. For example, icons should ideally inherit the current text color via `currentColor`, so you may need to apply `fill="currentColor` or `stroke="currentColor"` to the SVG element using this function. @@ -220,7 +223,7 @@ Here's an example that registers an icon library located in the `/assets/icons` import { registerIconLibrary } from '/dist/webawesome.js'; registerIconLibrary('my-icons', { - resolver: name => `/assets/icons/${name}.svg`, + resolver: (name, family, variant) => `/assets/icons/${name}.svg`, mutator: svg => svg.setAttribute('fill', 'currentColor') }); @@ -237,6 +240,25 @@ If an icon is used before registration occurs, it will be empty initially but sh The following examples demonstrate how to register a number of popular, open source icon libraries via CDN. Feel free to adapt the code as you see fit to use your own origin or naming conventions. +### Bootstrap Icons + +This will register the [Bootstrap Icons](https://icons.getbootstrap.com/) library using the jsDelivr CDN. This library has two families: `regular` and `filled`. + +Icons in this library are licensed under the [MIT License](https://github.com/twbs/icons/blob/main/LICENSE). + +```html + +``` + ### Boxicons This will register the [Boxicons](https://boxicons.com/) library using the jsDelivr CDN. This library has three variations: regular (`bx-*`), solid (`bxs-*`), and logos (`bxl-*`). A mutator function is required to set the SVG's `fill` to `currentColor`. @@ -587,16 +609,19 @@ Icons in this library are licensed under the [Apache 2.0 License](https://github ### Customizing the Default Library -The default icon library contains over 1,300 icons courtesy of the [Bootstrap Icons](https://icons.getbootstrap.com/) project. These are the icons that display when you use `` without the `library` attribute. If you prefer to have these icons resolve elsewhere or to a different icon library, register an icon library using the `default` name and a custom resolver. +The default icon library contains over 2,000 icons courtesy of [Font Awesome](https://fontawesome.com/). These are the icons that display when you use `` without the `library` attribute. If you prefer to have these icons resolve elsewhere or to a different icon library, register an icon library using the `default` name and a custom resolver. -This example will load the same set of icons from the jsDelivr CDN instead of your local assets folder. +For example, this will change the default icon library to use [Bootstrap Icons](https://icons.getbootstrap.com/) loaded from the jsDelivr CDN. ```html ``` From 39b5737a7f058370eacc4f9b2bf64fe7f1a55c19 Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 14:38:05 -0400 Subject: [PATCH 09/11] expose kit functions --- src/webawesome.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/webawesome.ts b/src/webawesome.ts index 656bd8aed..a1b006aa6 100644 --- a/src/webawesome.ts +++ b/src/webawesome.ts @@ -1,4 +1,4 @@ -export { getBasePath, setBasePath } from './utilities/base-path.js'; +export { getBasePath, setBasePath, getKitCode, setKitCode } from './utilities/base-path.js'; export { registerIconLibrary, unregisterIconLibrary } from './components/icon/library.js'; export { discover } from './utilities/autoloader.js'; From 5d5ac5576e7019dfc9bf6c7fb3709b57a4910ea5 Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 14:38:11 -0400 Subject: [PATCH 10/11] update comments --- src/components/icon/icon.ts | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/src/components/icon/icon.ts b/src/components/icon/icon.ts index bff9e5b46..2df51e9ef 100644 --- a/src/components/icon/icon.ts +++ b/src/components/icon/icon.ts @@ -52,14 +52,16 @@ export default class WaIcon extends WebAwesomeElement { @property({ reflect: true }) name?: string; /** - * The family of icons to choose from. For Font Awesome, valid options include `classic`, `sharp`, `duotone`, and - * `brands`. Custom icon libraries may or may not use this property. + * The family of icons to choose from. For Font Awesome Free (default), valid options include `classic` and `brands`. + * For Font Awesome Pro subscribers, valid options include, `classic`, `sharp`, `duotone`, and `brands`. Custom icon + * libraries may or may not use this property. */ @property({ reflect: true }) family: string; /** * The name of the icon's variant. For Font Awesome, valid options include `thin`, `light`, `regular`, and `solid` for - * the _classic_ and _sharp_ families. Custom icon libraries may or may not use this property. + * the `classic` and `sharp` families. Some variants require a Font Awesome Pro subscription. Custom icon libraries + * may or may not use this property. */ @property({ reflect: true }) variant: string; From 530673dcd1f045d479973ffb829ffae6fdff5a40 Mon Sep 17 00:00:00 2001 From: Cory LaViska Date: Tue, 11 Jun 2024 14:38:22 -0400 Subject: [PATCH 11/11] change data attrib --- src/utilities/base-path.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/utilities/base-path.ts b/src/utilities/base-path.ts index ef5e7e8cb..94980c0cc 100644 --- a/src/utilities/base-path.ts +++ b/src/utilities/base-path.ts @@ -55,20 +55,20 @@ export function setKitCode(code: string) { * Gets the library's Web Awesome kit code. * * The kit code is used to fetch premium assets, so it needs to be set for certain components to work correctly. This - * isn't something we can infer, so the user will need to provide it using the `data-webawesome-kit` attribute. This can + * isn't something we can infer, so the user will need to provide it using the `data-fa-kit-code` attribute. This can * be on any element, but ideally it should exist on the script that imports Web Awesome. * - * + * * * Alternatively, you can set the kit code manually using the exported `setKitCode()` function. * */ export function getKitCode() { if (!kitCode) { - const el = document.querySelector('[data-webawesome-kit]'); + const el = document.querySelector('[data-fa-kit-code]'); if (el) { - setKitCode(el.getAttribute('data-webawesome-kit') || ''); + setKitCode(el.getAttribute('data-fa-kit-code') || ''); } }