Compare commits

..

1599 Commits

Author SHA1 Message Date
Cory LaViska
5e6e0368a4 Merge branch 'next' into current 2023-08-23 12:58:35 -04:00
Cory LaViska
7e4d4c3c98 2.8.0 2023-08-23 12:55:35 -04:00
Cory LaViska
b5ef3191b7 update version 2023-08-23 12:53:47 -04:00
Konnor Rogers
f30481e229 remove unused code path (#1539) 2023-08-23 12:52:42 -04:00
Konnor Rogers
ae010c333b fix: check <slot> elements for assignedElements to allow wrapping focus-trapped elements (#1537)
* fix: internal logic for tabbable checks slotted elements

* prettier

* add better note for generators

* prettier

* fix tests

* prettier

* prettier

* fix tabbable test for safari

* prettier

* Update src/internal/tabbable.ts

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>

* Update src/internal/modal.ts

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>

* Update src/internal/tabbable.ts

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>

---------

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2023-08-23 11:43:48 -04:00
Konnor Rogers
43d1f9ee7a fix: use verbatimModuleSyntax and isolatedModules (#1534)
* feat: use verbatimModuleSyntax and isolatedModules

* prettier

* remove newline

* prettier
2023-08-23 10:34:40 -04:00
Cory LaViska
ec17e8736d fix component links; closes #1538 2023-08-23 09:46:23 -04:00
Cory LaViska
44b27e791e fix plop template 2023-08-23 09:29:24 -04:00
Cory LaViska
02385027db fix copy button focus 2023-08-22 17:10:01 -04:00
Cory LaViska
b311072d9b use <sl-copy-button> (#1535) 2023-08-22 17:01:00 -04:00
Cory LaViska
87ac077b0a fix empty attributes in properties table (#1536) 2023-08-22 16:59:08 -04:00
Konnor Rogers
87837df35c remove extra react component wrapper, upgrade to v2 of @lit-labs/react (#1531)
* remove extra react wrapper, upgrade to v2 of @lit-labs/react, call define in module.

* add changelog entry

* prettier
2023-08-22 11:26:54 -04:00
Konnor Rogers
5d72bbd162 remove baseUrl from tsconfig for better dev experience (#1530) 2023-08-22 10:32:15 -04:00
Cory LaViska
a4fc1c5b44 Submenus (#1527)
* [RFC] Proof-of-concept commit for submenu support

This is a Request For Comments to seek directional guidance towards
implementing the submenu slot of menu-item.

Includes:
- SubmenuController to manage event listeners on menu-item.
- Example usage in menu-item documentation.
- Trivial tests to check rendering.

Outstanding questions include:
- Accessibility concerns. E.g. where to handle 'ArrowRight',
  'ArrowLeft'?
- Should selection of menu-item denoting submenu be possible or
  customizable?
- How to parameterize contained popup?
- Implementation concerns:
  - Use of ref / id
  - delegation of some rendering to the controller
  - What to test

Related to [#620](https://github.com/shoelace-style/shoelace/issues/620).

* Update submenu-controller.ts

Removed extraneous `console.log()`.

* PoC working of ArrowRight to focus on submenu.

* Revert "PoC working of ArrowRight to focus on submenu."

(Didn't mean to publish this.)

This reverts commit be04e9a221.

* [WIP] Submenu WIP continues.

- Submenus now close on change-of-focus, not a timeout.
- Keyboard navigation support added.
- Skidding fix for better alignment.
- Submenu documentation moved to Menu page.
- Tests for accessibility, right and left arrow keys.

* Cleanup: Removed dead code and dead code comments.

* style: Eslint warnings and errors fixed. npm run verify now passes.

* fix: 2 changes to menu / submenu on-click behavior:

1. Close submenu on click explicitly, so this occurs even if the menu is
   not inside of an sl-dropdown.

2. In menu, ignore clicks that do not explicitly target a menu-item.
   Clicks that were on (e.g. a menu-border) were emitting select events.

* fix: Prevent menu's extraneous Enter / space key propagation.

Menu's handleKeyDown calls item.click (to emit the selection).
Propagating the keyboard event on Enter / space would the cause re-entry
into a submenu, so prevent the needless propagation.

* Submenu tweaks ...

- 100 ms delay when opening submenus on mouseover
- Shadows added
- Distance added to popup to have submenus overlap menu slightly.

* polish up submenu stuff

* stay highlighted when submenu is open

* update changelog

* resolve feedback

---------

Co-authored-by: Bryce Moore <bryce.moore@gmail.com>
2023-08-21 17:26:41 -04:00
Konnor Rogers
539eaded73 Update React Wrappers with Refs that work (#1526)
* fix react types for refs

* fix displayName

* fix displayName]

* attempt to fix typings for React refs

* fix bad type

* prettier

* add changelog entry

* prettier
2023-08-18 13:31:50 -04:00
Cory LaViska
93b2e78092 Merge branch 'nathangray-next' into next 2023-08-18 12:05:47 -04:00
Cory LaViska
402a00dcd3 update docs 2023-08-18 12:05:22 -04:00
Cory LaViska
b63368d5f6 Merge branch 'next' of github.com:nathangray/shoelace into nathangray-next 2023-08-18 11:23:56 -04:00
Cory LaViska
74c6d3ee36 fix tree tests; #1521 2023-08-18 11:20:14 -04:00
nathan
621aa4362b Add HTMLElement to the getTag() return type 2023-08-18 09:17:02 -06:00
Cory LaViska
c8919ad11f prettier 2023-08-18 09:55:57 -04:00
Stephen Sugden
fad76dd1a2 SlTree: separate expand/collapse and selection behaviour in 'single' mode (#1521)
* Never select tree items when clicking the chevron

This changes the behaviour of sl-tree so that clicking on the expand/collapse icon will not select/deselect the item, only toggle it's expanded state.

* Refactor: inline SlTree.syncTreeItems

This was only called from 2 places, and they each had different
behaviour anyways.

* SlTree: separate expand/collapse from selection

This makes 'multi' and 'single' mode consistent with each other, and
with native file managers.
2023-08-18 09:55:29 -04:00
nathan
b2f6499b87 Fix lint warnings 2023-08-17 13:18:51 -06:00
nathan
9520e850dd Update for path changes
see 3a61d20d93
2023-08-17 11:34:25 -06:00
Cory LaViska
4ee5271a83 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-08-16 15:01:46 -04:00
Thomas Allmer
d8de7bcc51 fix(docs): Inline Form Validation Docs throw error on top level await (#1522) 2023-08-16 14:59:21 -04:00
Cory LaViska
7ee31be6d6 ignore package.json 2023-08-16 14:57:03 -04:00
Cory LaViska
9cb5ba7ac1 Radio button fix (#1524)
* fix formatting

* fix radio button spacing; fixes #1523
2023-08-16 14:51:46 -04:00
Peter Siska
c380368b61 Fix NPMDIR config (#1518)
* Fix NPMDIR config

* Add missing semi
2023-08-15 10:46:51 -04:00
Konnor Rogers
e298f7e5f4 fix broken tests for shoelace-element (#1516)
* add stub code prior to test

* fix broken test

* prettier

* prettier

* prettier
2023-08-14 11:23:00 -04:00
Cory LaViska
c743561c25 update docs 2023-08-14 10:23:59 -04:00
Alexander Krolick
e73e32fb71 Add docs on setting multiple values in select (#1508) 2023-08-14 10:21:52 -04:00
Cory LaViska
b09a48bec4 fix arg name 2023-08-14 10:02:23 -04:00
Burton Smith
aeef986cf5 JetBrains IDE Integration (#1512)
* upgrade vs code integration package

* add references

* add web-types plugin

* update reference

* run prettier

* update documentation

* run prettier

* remove test script
2023-08-14 09:34:34 -04:00
Cory LaViska
409ac96ddf Merge branch 'next' into current 2023-08-11 13:27:07 -04:00
Cory LaViska
6f08f50639 2.7.0 2023-08-11 13:16:46 -04:00
Cory LaViska
8fc5f598d0 update changelog 2023-08-11 13:13:00 -04:00
Cory LaViska
1383ea3fe8 React import paths (#1507)
* fix react imports in examples

* move types to definition files

* update changelog

* update changelog
2023-08-11 13:09:44 -04:00
king8fisher
f8c37e0d14 Fix missing comma in linear-gradient (#1506) 2023-08-11 13:06:10 -04:00
Cory LaViska
cf543ef335 don't hijack key presses in text fields; fixes #1492 (#1504) 2023-08-11 11:25:46 -04:00
Cory LaViska
a3450a7d83 move emphasis 2023-08-11 11:01:37 -04:00
Cory LaViska
e80b2c9fb9 prettier 2023-08-11 11:01:00 -04:00
Alexander Krolick
8d617fb98c Expand on comment about space-separated value for sl-select (#1502) 2023-08-11 10:58:14 -04:00
Burton Smith
a6e225e47c upgrade vs code integration package (#1500)
* upgrade vs code integration package

* add references
2023-08-11 10:51:33 -04:00
Cory LaViska
e21943f4fb fix typos/whitespace 2023-08-11 10:30:40 -04:00
Cory LaViska
c36df5ecc1 <sl-copy> (#1483)
* copy updates

* Update docs/pages/components/copy.md

Co-authored-by: Thomas Allmer <d4kmor@gmail.com>

* unwrap and fix case

* copy button updates

* use bs icon

* add parts, hoist, and improve parsing a bit

* update docs

* remove comment

---------

Co-authored-by: Thomas Allmer <d4kmor@gmail.com>
2023-08-11 10:27:34 -04:00
Cory LaViska
458def7830 update bootstrap icons and fix license 2023-08-10 12:59:44 -04:00
Cory LaViska
b5d800f07a don't wrap code tags in tables 2023-08-10 11:29:25 -04:00
Cory LaViska
6551a6330b remove default assignee 2023-08-09 16:13:52 -04:00
Cory LaViska
cb5f670909 update changelog 2023-08-09 15:40:36 -04:00
Cory LaViska
5b6c1632bd update var names and use stylesheet; #1496 2023-08-09 15:38:24 -04:00
Tomas Drencak
bf15f2fb8a Toggle visibility of the clear button (#1496) 2023-08-09 15:28:30 -04:00
Konnor Rogers
31ef2f7929 remove side-effects key, update React docs for cherry-picking (#1485)
* remove side-effects, update React docs for cherry-picking

* prettier

* add PR #

* prettier

* fix react import paths

* Update docs/pages/frameworks/react.md

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>

* add colons to imports

---------

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2023-08-07 13:20:34 -04:00
Cory LaViska
8aab94f184 switch skypack to esm.sh to fix react examples 2023-08-03 15:27:10 -04:00
Cory LaViska
b7acb27c98 Revert "feat(clipboard): add new component sl-clipboard (#1473)"
This reverts commit 16f3e256b0.
2023-08-02 15:35:11 -04:00
Cory LaViska
dcbbc55f28 fix up/down focus in dropdown; closes #1472 (#1481) 2023-08-01 14:05:11 -04:00
Konnor Rogers
81dfcc2eae fix treeshaking array (#1480)
* fix treeshaking array

* fix treeshaking array

* imports to not use .component
2023-08-01 14:04:36 -04:00
Thomas Allmer
16f3e256b0 feat(clipboard): add new component sl-clipboard (#1473)
* feat(clipboard): add new component sl-clipboard

* using slots

* using a single copyStatus

* feat(clipboard): support inputs/textarea/links and shadow dom

* fix(clipboard): add area-live to announce copied

* feat(clipboard): support any component with a value property
2023-08-01 13:53:11 -04:00
Cory LaViska
1bf09f20aa Merge branch 'next' into current 2023-07-31 15:49:04 -04:00
Cory LaViska
75b2da9eab 2.6.0 2023-07-31 15:17:43 -04:00
Cory LaViska
9736f053d9 update version 2023-07-31 15:15:54 -04:00
Cory LaViska
d0b710c26d clear search index and other cache with cmd+shift+r 2023-07-31 15:14:25 -04:00
Cory LaViska
5b83d4d1b0 update changelog 2023-07-31 14:00:57 -04:00
Thomas Allmer
89f0f4a02c feat(details): use details and summary html tag to enable in browser searching (#1470) 2023-07-31 13:58:42 -04:00
Cory LaViska
a067ccb9e0 fix docs 2023-07-27 12:39:44 -04:00
Cory LaViska
1ccea42cca fix card borders 2023-07-26 15:20:51 -04:00
Cory LaViska
0f90dd0f54 update changelog 2023-07-25 22:20:13 -04:00
Ben Anderson
262cbc9a22 Add entry to changelog for types for react-wrapped elements (#1464) 2023-07-25 22:18:54 -04:00
Konnor Rogers
3a61d20d93 Create non-auto-registering routes (#1450)
* initial attempt at not auto defining

* add files with -

* continued work on removing auto-define

* fix component definitions

* update with new tag stuff

* fix lots of things

* fix improper scoped elements

* working through side effects

* continued react wrapper work

* update changelog

* formatting

* fixes

* update changelog

* lint / formatting

* fix version injection

* fix version injection, work on test

* fix version injection, work on test

* fix merge conflicts

* fix jsdoc null issue

* fix templates

* use exports

* working on tests

* working on registration mocking

* fix customElements test

* linting

* fix some test stuff

* clean up test

* clean up comment

* rename scopedElements to dependencies

* linting / formatting

* linting / formatting

* mark all packages external and still bundle

* set bundle false

* set bundle true

* dont minify

* fix merge conflicts

* use built shoelace-element

* fix lint errors

* prettier

* appease eslint

* appease eslint gods

* appease eslint gods

* appease eslint gods

* appease eslint gods

* add shoelace-autoloader

* move it all into 1 function

* add exportmaps note

* prettier

* add jsdelivr entrypoint

* read as utf8

* update docs with .component.js importS

* prettier
2023-07-24 13:00:07 -04:00
Cory LaViska
95f4f87eb8 update changelog 2023-07-19 15:06:25 -04:00
Cory LaViska
5b3cc0d492 add part to docs; #1460 2023-07-19 15:05:52 -04:00
Yehuda Ringler
0de39a8163 Add part to button spinner (#1460) 2023-07-19 15:04:49 -04:00
Cory LaViska
879fd7a224 wait for registration before attaching form handlers; closes #1452 2023-07-18 13:38:20 -04:00
Cory LaViska
50af138424 fix typos 2023-07-18 13:15:21 -04:00
Cory LaViska
9d592f4e08 wait longer to prevent flakiness 2023-07-18 13:13:59 -04:00
Cory LaViska
5016d27af7 remove test because we can't reliably suppress retargeted clicks 2023-07-18 13:11:08 -04:00
Chellappan
7218a19357 Replace .bind() with arrow functions in form controller,modal and slot controller (#1453) 2023-07-18 13:05:00 -04:00
Cory LaViska
33d2d4368f fix logic 2023-07-18 13:03:34 -04:00
Cory LaViska
cca40ca710 remove test because we can't reliably prevent retargeted click handlers 2023-07-18 12:58:22 -04:00
Cory LaViska
c6281859fd remove dead logic 2023-07-18 12:49:22 -04:00
Cory LaViska
956271880d fix for contained 2023-07-18 12:39:44 -04:00
Cory LaViska
201ff4efc5 fix escape key in dialog/drawer; closes #1457 2023-07-18 12:37:52 -04:00
Cory LaViska
f954233bda Revert "Move keydown handler for sl-drawer back to base div (#1459)"
This reverts commit 1e243e4257.
2023-07-18 12:12:43 -04:00
Cory LaViska
8267968b76 update output 2023-07-18 12:08:50 -04:00
Stephen Sugden
1e243e4257 Move keydown handler for sl-drawer back to base div (#1459)
* Move keydown handler for sl-drawer back to base div

This restores the stacking behaviour of drawers

See: #1457

* Autofocus panel of sl-drawer when it is open on firstUpdate
2023-07-18 11:57:16 -04:00
Cory LaViska
0b6c3a46cf Quick fixes (#1458)
* update base path docs

* fix examples

* fix broken CEM data in <sl-popup>

* Update docs/pages/getting-started/installation.md

Co-authored-by: Lindsay M <126139086+lindsaym-fa@users.noreply.github.com>

---------

Co-authored-by: Lindsay M <126139086+lindsaym-fa@users.noreply.github.com>
2023-07-17 14:05:17 -04:00
Cory LaViska
a2e58b7696 fix link 2023-07-17 10:05:00 -04:00
Cory LaViska
119d299657 remove old SPA settings 2023-07-13 17:00:23 -04:00
Cory LaViska
e8634e4178 Popup virtual elements (#1449)
* 1433: POC for comments (+ fix build.watch())

* 1433: consolidate virtualAnchor into anchor

* add virtual element examples

* update changelog

---------

Co-authored-by: Marko <marko@modelcitizen.com>
2023-07-13 16:49:57 -04:00
Cory LaViska
2e2a683d11 cleanup /index.html from search results (#1454) 2023-07-13 16:20:26 -04:00
Cory LaViska
414197acc9 unset last focused item; #1436 (#1446) 2023-07-12 14:52:13 -04:00
Ben Anderson
8fd01e1eda Add event types to react wrapper components (#1419)
* Rename SlSlideChange for consistency with other events

* Setup React event types for events used by Shoelace components

Means that consumers of Shoelace via the React wrapper will be able to
use callback methods with the correct event type, instead of having to
rely on casting and friends when using Typescript.

* Add docs demonstrating importing event types for React callbacks
2023-07-12 11:31:27 -04:00
Cory LaViska
e1ca7d1f59 Lit a11y update (#1444)
* update eslint-plugin-lit-a11y to latest

* update eslint deps

* remove aria- and role attribs from slots; closes #1422
2023-07-12 11:12:15 -04:00
Cory LaViska
f84d6939bd Doc updates (#1445)
* rename to CSS parts

* fix double dashes from merging
2023-07-11 15:23:51 -04:00
Konnor Rogers
82446e2114 Add modal tab tracking (#1403)
* add modal tab tracking

* prettier

* sort by tabindex

* sort by tabindex

* add a dialog test case for shadow roots

* add a changelog note

* add a changelog note

* prettier + test fixes

* prettier + test fixes
2023-07-07 15:32:23 -04:00
Konnor Rogers
a4f0ae9088 fix: valueAsDate now falls back to native implementation (#1399)
* fix: valueAsDate now falls back to native implementation

* changelog

* prettier

* prettier
2023-07-07 13:51:22 -04:00
Cory LaViska
fe3906f766 Don't steal focus when removing focused tree items (#1430)
* don't steal focus when removing focused tree items; #1428

* update PR link
2023-07-06 10:36:41 -04:00
Cory LaViska
c9e644f3fc Allow selecting menu items with space (#1429)
* allow selecting menu items with space; #1423

* update PR
2023-07-06 10:36:29 -04:00
Cory LaViska
8ffbd02db7 update changelog 2023-07-05 16:32:59 -04:00
Evan Harrison
e88d57d17d change .floor to .ceil in getCurrentPage; modify prev function to return to closest previous snappable index (#1420) 2023-07-05 16:26:00 -04:00
Cory LaViska
5f4de6d9f5 skip flaky tests 2023-07-03 15:59:24 -04:00
Cory LaViska
2cce87deeb add links 2023-07-03 15:50:58 -04:00
Cory LaViska
630b5b19a0 fix regression; #1417 2023-07-03 15:49:25 -04:00
Cory LaViska
2ce1451a9f fix typo 2023-07-03 15:17:43 -04:00
Cory LaViska
2d1badba96 this is why we can't have nice things 2023-07-03 13:31:28 -04:00
Cory LaViska
1b5db078a7 move aria attribs off <slot>; fixes #1417 2023-07-03 12:39:42 -04:00
Cory LaViska
91095bd63a better description for lighthouse 2023-07-03 12:38:09 -04:00
Cory LaViska
d9703a64fd restore concurrency 2023-07-03 11:25:43 -04:00
Cory LaViska
4c22e72390 update changelog 2023-07-03 11:21:39 -04:00
dhellgartner
d05b8fca20 Qr code tests (#1416)
* Add tests for qr-code

* Fix a small bug in qr-code

The background color was not passed to the
qr code

---------

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-07-03 11:19:50 -04:00
Evan Harrison
afca2ad2e0 change carousel docs to use correct attr name, slides-per-page (#1415) 2023-07-03 11:14:15 -04:00
Cory LaViska
b2aa854d98 update docs 2023-06-28 15:27:21 -04:00
Cory LaViska
ba642a0886 Merge branch 'next' into current 2023-06-26 12:26:48 -04:00
Cory LaViska
287fff7cf1 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-06-26 12:25:30 -04:00
Cory LaViska
136ecae4a6 2.5.2 2023-06-26 12:21:04 -04:00
Cory LaViska
cac772d5e6 update version 2023-06-26 12:20:55 -04:00
Cory LaViska
e1dedcb1b5 Fix broken links (#1407)
* add spacing

* update old links
2023-06-26 12:20:13 -04:00
Cory LaViska
c4901eca68 update old links 2023-06-26 12:17:48 -04:00
Cory LaViska
a001c2d12b add spacing 2023-06-26 12:11:15 -04:00
Eddie Cheng R4
c4c622eabd redirect the link to the right page (#1404) 2023-06-26 12:08:54 -04:00
Cory LaViska
1ae018bedd fix broken source buttons in docs (#1401) 2023-06-23 12:03:51 -04:00
Cory LaViska
c37c71d8fd Merge branch 'next' into current 2023-06-22 11:25:55 -04:00
Cory LaViska
24929e27c1 skip 2023-06-22 11:23:45 -04:00
Cory LaViska
33a8d92aec update version 2023-06-22 11:11:11 -04:00
Cory LaViska
32d21fa560 2.5.1 2023-06-22 11:10:15 -04:00
Cory LaViska
347d8b7f79 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-06-22 11:04:34 -04:00
Cory LaViska
8f9c15913b update changelog 2023-06-22 11:04:33 -04:00
Konnor Rogers
60d7f688eb fix extensionless imports (#1394) 2023-06-22 10:56:24 -04:00
Cory LaViska
15f914914c simplify theme toggle 2023-06-22 10:47:41 -04:00
Alan Chambers
2914475821 docs changed theme toggle to theme selector (#1395) 2023-06-22 10:44:08 -04:00
Konnor Rogers
8e831aa3e7 fix source flavors (#1388)
* fix load flavor

* Update docs/assets/scripts/code-previews.js

* fix previews

---------

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2023-06-21 11:12:09 -04:00
Cory LaViska
985d4585c4 fixes #1387 (#1392) 2023-06-21 11:07:02 -04:00
Cory LaViska
05b1212657 Merge branch 'next' into current 2023-06-20 15:31:04 -04:00
Cory LaViska
854db13bd7 2.5.0 2023-06-20 15:26:55 -04:00
Cory LaViska
4ddf80459a ignore 2023-06-20 15:25:04 -04:00
Cory LaViska
89fc2ff643 update version 2023-06-20 15:24:21 -04:00
Konnor Rogers
d7145f1f84 Konnorrogers/fix value as number 2 (#1385)
* fix: garbage collected valueAs*

* weird....

* prettier and tests
2023-06-20 15:22:13 -04:00
Konnor Rogers
441a957432 fix: <sl-carousel> has the wrong import for LocalizeController (#1384)
* fix autoloading translations

* add changelog entry

* prettier

* prettier
2023-06-20 14:02:07 -04:00
Konnor Rogers
67cbb85682 Add support for svg sprites in <sl-icon> (#1374)
* wip: initial implementation for review

* icon testing

* feat: add the ability to use SVG sprite sheets

* finish up spritesheets

* add icon notes

* update plopfile, add changelog entry

* prettier

* linting

* linting

* fix icon test

* eslint fixes?

* prettier

* disable eslint -.-

* linting loop!

* linting loop!

* prettier

* prettier

---------

Co-authored-by: Diego <diego@trebellar.com>
2023-06-20 14:01:58 -04:00
Cory LaViska
0005d16a06 fixes #1380 2023-06-19 15:13:48 -04:00
Cory LaViska
ca5ab03cd4 update docs 2023-06-19 10:12:01 -04:00
Konnor Rogers
c9e30022df overeager %CDNDIR% in sandbox previews. (#1377)
* overeager with sandboxes

* prettier
2023-06-15 13:25:12 -04:00
Konnor Rogers
c167bdd80f Merge pull request #1372 from justinfagnani/no-bind
Code size optimizations: Replace .bind() with arrow functions, add listeners in constructors.
2023-06-15 11:58:08 -04:00
Justin Fagnani
b9f62bb1bc Migrate SlCarousel.handleSlotChange 2023-06-14 15:16:26 +09:00
Justin Fagnani
a01b2cf8a2 Replace .bind() with arrow functions, add listeners in constructors. 2023-06-14 08:52:12 +09:00
Konnor Rogers
f4b2623c8f Merge pull request #1371 from shoelace-style/konnorrogers/fix-the-tests
fix the tests
2023-06-13 16:11:54 -04:00
konnorrogers
af8426579e prettier 2023-06-13 15:59:16 -04:00
konnorrogers
6b9ba9becf eslint 2023-06-13 15:54:09 -04:00
konnorrogers
c6cc7b6983 prettier 2023-06-13 15:43:21 -04:00
konnorrogers
0e869ec18d fix the tests 2023-06-13 15:40:04 -04:00
Cory LaViska
1b347874ef fix tests 2023-06-13 14:22:56 -04:00
Cory LaViska
ff5b1e8573 fix imports 2023-06-13 14:06:37 -04:00
Cory LaViska
73ad76a2fa fix serve 2023-06-13 13:48:50 -04:00
Konnor Rogers
aadcb486a9 fix broken build (#1370)
* fix broken build

* prettier
2023-06-13 12:30:32 -04:00
Cory LaViska
4c854d64a7 upgrade lit 2023-06-13 12:19:39 -04:00
Cory LaViska
c2e02d34ad remove log 2023-06-13 12:19:34 -04:00
Cory LaViska
8c8977549c fix dispose 2023-06-13 12:19:25 -04:00
Cory LaViska
24ef154d42 update esbuild 2023-06-13 11:48:17 -04:00
Cory LaViska
b5a3045bae update typescript 2023-06-13 11:37:33 -04:00
Cory LaViska
7404e496cb Merge branch 'konnorrogers/modify-build-script-for-npm-2' into next 2023-06-13 10:05:00 -04:00
konnorrogers
5ba2c7eeec watch cdn, not dist 2023-06-13 09:31:02 -04:00
Cory LaViska
514a7f3d51 Merge branch 'konnorrogers/modify-build-script-for-npm-2' of https://github.com/shoelace-style/shoelace into konnorrogers/modify-build-script-for-npm-2 2023-06-12 16:24:24 -04:00
Cory LaViska
15474b83b1 update 2023-06-12 16:24:21 -04:00
konnorrogers
a5f1bc6c82 fix circular dependency 2023-06-12 16:23:47 -04:00
Cory LaViska
834d44e0e4 npm 2023-06-12 16:22:20 -04:00
Cory LaViska
c070149ae6 update + formatting 2023-06-12 16:22:08 -04:00
Cory LaViska
b0b6ea943e use cdn bundle for docs 2023-06-12 16:15:52 -04:00
Cory LaViska
65b72217ea remove copydir and fix virtual path for serve 2023-06-12 16:15:29 -04:00
Cory LaViska
c4c2e8e3a9 make esbuild happy again 2023-06-12 15:36:35 -04:00
Cory LaViska
47018d61cd don't bundle anything for npm 2023-06-12 15:32:45 -04:00
konnorrogers
d18db9adfa prettier 2023-06-12 14:20:11 -04:00
konnorrogers
41913c8c58 update docs with cdn / npm paths 2023-06-12 13:45:27 -04:00
konnorrogers
68b982a744 update docs 2023-06-12 12:48:15 -04:00
Cory LaViska
a582302a79 update changelog 2023-06-12 12:13:18 -04:00
Brendon Muir
bd3b2c93ee Fix sl-input[type="date|time"] placeholder on macOS Safari (#1341)
Allowing the background to inherit rather than removing it allows the weird date and time placeholder text opacity to work on macOS Safari.
2023-06-12 12:09:20 -04:00
konnorrogers
4704d63791 Merge branch 'konnorrogers/modify-build-script-for-npm-2' of https://github.com/shoelace-style/shoelace into konnorrogers/modify-build-script-for-npm-2 2023-06-12 11:40:01 -04:00
konnorrogers
415a1477bb changelog, prettier 2023-06-12 11:39:56 -04:00
Cory LaViska
f363d5e187 Merge branch 'next' into konnorrogers/modify-build-script-for-npm-2 2023-06-12 11:36:23 -04:00
Cory LaViska
efb0ee9c48 fix spelling 2023-06-12 11:36:08 -04:00
konnorrogers
96daee5e1a use cdn dir for testing 2023-06-12 11:18:24 -04:00
konnorrogers
d236206cce remove unneeded CLI args 2023-06-12 10:54:33 -04:00
Konnor Rogers
1ef8e1cf73 fix: radio group race condition (#1364)
* fix: radio group race condition

* update changelog

* prettier

* fix changelog
2023-06-08 15:45:34 -04:00
Cory LaViska
dc63f858b0 fix typo 2023-06-08 15:41:03 -04:00
Cory LaViska
b8a3952153 show next/dev versiosn 2023-06-08 15:33:36 -04:00
Cory LaViska
4b2a62f660 prettier 2023-06-08 15:27:32 -04:00
Cory LaViska
08c074e44b prettier 2023-06-08 15:24:56 -04:00
Cory LaViska
d1953b0215 Merge branch 'new-docs' into next 2023-06-08 15:22:02 -04:00
Cory LaViska
b268d7dd8e done! 2023-06-08 15:12:23 -04:00
Cory LaViska
90e56e2f07 don't swallow errors 2023-06-08 15:05:39 -04:00
Cory LaViska
45ddaa4d38 cleaner watching 2023-06-08 14:46:12 -04:00
Cory LaViska
0de54b163a smarter exit 2023-06-08 13:47:01 -04:00
Cory LaViska
620b86cddb exit after 2023-06-08 12:51:15 -04:00
Cory LaViska
32d0ac4147 remove extra heading 2023-06-08 12:39:18 -04:00
Cory LaViska
a16733eb93 don't allow numbers at the start of an id 2023-06-08 12:39:12 -04:00
Cory LaViska
b67eef484c prettier 2023-06-08 12:23:31 -04:00
Konnor Rogers
5166964659 fix scroll spy 2023-06-08 12:15:02 -04:00
Cory LaViska
e72c2df6d2 fixes for turbo 2023-06-08 12:02:24 -04:00
Cory LaViska
cdafb3870c use delegation so resizing works with turbo 2023-06-08 11:26:25 -04:00
Cory LaViska
20abf21791 move scripts to <head> and defer for turbo 2023-06-08 11:12:31 -04:00
Konnor Rogers
482d155af4 add turbo 2023-06-08 00:15:07 -04:00
Konnor Rogers
ece23c727e add turbo 2023-06-07 17:23:57 -04:00
Cory LaViska
b7726cd514 cleanup 2023-06-07 16:56:46 -04:00
Cory LaViska
c31fe1ed35 update template 2023-06-07 16:53:48 -04:00
Cory LaViska
9e034810d9 reorder 2023-06-07 16:50:30 -04:00
Cory LaViska
217aabe55a update plop 2023-06-07 16:49:27 -04:00
Cory LaViska
1dea2f384e reorder 2023-06-07 16:47:28 -04:00
Cory LaViska
c24edec6b9 sync changelog 2023-06-07 16:43:03 -04:00
Cory LaViska
add09ca5b8 cleanup 2023-06-07 16:38:13 -04:00
Cory LaViska
57bd3632e8 fix spinner in prod build 2023-06-07 16:16:00 -04:00
Cory LaViska
6f44b6ffa6 remove await 2023-06-07 16:14:32 -04:00
Cory LaViska
ca8ba2d16b don't swallow errors 2023-06-07 16:14:25 -04:00
Cory LaViska
c37e4ba6b5 don't hide cursor 2023-06-07 15:19:10 -04:00
Cory LaViska
82cc778a0f fix urls when build on win 2023-06-07 14:03:04 -04:00
Cory LaViska
5085ef831b add shell for win 2023-06-07 13:49:10 -04:00
Cory LaViska
4721bd117b kill child processes without errors 2023-06-07 14:12:34 -04:00
Cory LaViska
57b13d848a nicer build (abort still erroring) 2023-06-07 13:28:22 -04:00
Cory LaViska
e01a43f01e rename vars 2023-06-07 07:54:05 -04:00
Cory LaViska
ec92351acf serve pages like page/index.html 2023-06-07 07:46:41 -04:00
Cory LaViska
8c44eb75d5 improvements 2023-06-06 17:02:15 -04:00
Konnor Rogers
aa48566aef make live reload actually work. 2023-06-06 15:46:50 -04:00
Scott Martin
7cbb26cbdb Correct import statement for all React components (#1363)
The current statement is incorrect and will result in
`Module not found: Package path ./dist/shoelace is not exported from package /your/path/to/node_modules/@shoelace-style/shoelace (see exports field in /your/path/to/node_modules/@shoelace-style/shoelace/package.json)`
2023-06-06 15:27:54 -04:00
Cory LaViska
b8b6175a64 works with a 24 second docs refresh 😕 2023-06-06 09:21:07 -04:00
Cory LaViska
de5ad1b1b9 new docs 2023-06-06 08:22:18 -04:00
Cory LaViska
0866785495 remove old docs 2023-06-06 08:20:35 -04:00
Cory LaViska
947b3a9ec4 support cjs 2023-06-06 08:18:44 -04:00
Cory LaViska
6db27ca51f update changelog 2023-06-01 08:57:03 -05:00
Yuki Nishijima
f966ba97d7 Update the tutorial for Rails (#1258)
* Update the tutorial for Rails

* Update docs/tutorials/integrating-with-rails.md

Co-authored-by: Konnor Rogers <konnor5456@gmail.com>

* Update docs/tutorials/integrating-with-rails.md

Co-authored-by: Konnor Rogers <konnor5456@gmail.com>

* Update docs/tutorials/integrating-with-rails.md

Co-authored-by: Konnor Rogers <konnor5456@gmail.com>

* Update docs/tutorials/integrating-with-rails.md

Co-authored-by: Konnor Rogers <konnor5456@gmail.com>

* Update docs/tutorials/integrating-with-rails.md

Co-authored-by: Konnor Rogers <konnor5456@gmail.com>

* Update docs/tutorials/integrating-with-rails.md

* Add a bit more explanation to set up icons

---------

Co-authored-by: Konnor Rogers <konnor5456@gmail.com>
2023-06-01 08:53:33 -05:00
Cory LaViska
1af711bc89 update changelog 2023-05-25 12:26:56 -04:00
dhellgartner
c71da4a075 Split panel tests (#1343)
* Added tests for sl-split-panel

test for horizontal arrangement

* Added tests for sl-split-panel

tests for vertical arrangement

---------

Co-authored-by: stefanie.hellgartner <stefanie.hellgartner@in-tech.com>
2023-05-25 12:25:48 -04:00
Cory LaViska
d609fa87b4 reflect size; fixes #1348 2023-05-25 10:47:44 -04:00
Cory LaViska
dd16b0f65f update form control guidelines 2023-05-25 10:29:15 -04:00
ErikOnBike
6144e5eff4 Replace .map with .forEach when return value not used. See issue #740 (#1349) 2023-05-24 10:34:42 -04:00
Bernhard
c4db99f5a3 update angular getting started (#1352) 2023-05-24 10:34:05 -04:00
Cory LaViska
21431b0e56 Remove outdated line from docs 2023-05-22 09:41:12 -04:00
Cory LaViska
136e6bc915 update changelog 2023-05-17 16:54:16 -04:00
Stefan Bauer
05aeb78b01 Update de.ts (#1339)
"Gleiten" is a verb and means glide, "Slide" must be translated with "Folie" (like in previousSlide, nextSlide)
2023-05-17 16:51:34 -04:00
Yuki Nishijima
22010a1f9b Add better support for Turbo Drive (#1338) 2023-05-17 16:50:34 -04:00
Erick Almeida
e0fd6b210e Fix Portuguese translation strings (#1336) 2023-05-16 07:55:17 -04:00
Konnor Rogers
be1c38f0e5 tests: add regression tests for checkbox and toggle focus behavior (#1330)
* add regression test for checkbox focusing

* change number of checkboxes / switches

* change max-height to 400px so it fails

* re-add positon: relative;
2023-05-10 16:54:44 -04:00
Cory LaViska
b1bdedd3a3 add submenu-icon part 2023-05-04 10:17:41 -04:00
Cory LaViska
429b47963b update changelog; #1310 2023-05-02 10:23:20 -04:00
Cory LaViska
466c8a0883 Merge branch 'mpharoah-mpharoah/sl-rating-perf' into next 2023-05-02 10:22:30 -04:00
Cory LaViska
3a212030c0 Merge branch 'mpharoah/sl-rating-perf' of github.com:mpharoah/shoelace into mpharoah-mpharoah/sl-rating-perf 2023-05-02 10:02:13 -04:00
Cory LaViska
7f1ac48f5f update changelog 2023-05-02 10:01:28 -04:00
Cory LaViska
9c3e344ae0 reorder properties 2023-05-02 10:01:25 -04:00
Cory LaViska
db147e77b0 Merge branch 'KonnorRogers-patch-1' into next 2023-05-02 10:00:14 -04:00
Cory LaViska
0384b03528 add checkbox + exported parts; #1318 2023-05-01 13:43:42 -04:00
Konnor Rogers
fc06de7b11 feat: support variable height elements inside <sl-button> 2023-04-28 22:31:42 -04:00
Cory LaViska
5ada0a7093 update radio size when group size changes 2023-04-27 13:18:21 -04:00
Cory LaViska
f136b8eb12 update docs; fixes #1315 2023-04-27 13:17:54 -04:00
Matt Pharoah
56a160464f Fixed clipPath 2023-04-21 08:56:43 -04:00
Matt Pharoah
3dc9430932 Improve performance of sl-rating by not render all icons twice 2023-04-20 17:01:12 -04:00
Cory LaViska
62b4525321 Merge branch 'next' into current 2023-04-14 13:01:22 -04:00
Cory LaViska
afa69b4f9c 2.4.0 2023-04-14 12:56:26 -04:00
Cory LaViska
102f46d185 bump version 2023-04-14 12:54:55 -04:00
Cory LaViska
9c5e184d82 fixes #1302 2023-04-14 12:48:57 -04:00
Cory LaViska
385b5451c8 add size to radio group; fixes #1301 2023-04-14 12:20:17 -04:00
Cory LaViska
0e7487257b spell check and reorder static function 2023-04-13 14:16:03 -04:00
Matt Pharoah
eab0e3219f Improve performance of sl-icon by caching later (#1286)
* Improve performance of sl-icon by caching later

* Fixed error handling

* Don't use requestInclude in sl-icon

* Separate sl-icon errors into cacheable and retryable errors
2023-04-13 14:12:59 -04:00
Cory LaViska
cf89c901a2 no roles on slots; fixes #1287 2023-04-13 12:52:03 -04:00
Cory LaViska
902b08cc0f revert role and don't use <header> for buttons 2023-04-13 12:47:48 -04:00
Cory LaViska
caf9a09efa fix typos 2023-04-13 12:47:18 -04:00
dhellgartner
65734dc993 Slot aria attributes (#1296)
* Fix acessability issue

* Additionally adapted the test

* Added more accessability tests

* Updated the testing documentation

to take the fact that accessability checks cover only
rendered content into account

---------

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-04-13 12:45:52 -04:00
Cory LaViska
0f02fffc3a less pipeline flakes 🤞🏻 2023-04-13 11:58:46 -04:00
Cory LaViska
931ecad8c5 update changelog 2023-04-13 11:56:33 -04:00
Alessandro
c137f83df6 fix(carousel): clickable elements don't work on chrome (#1266)
* fix(carousel): clickable elements don't work on chrome

* fix: update implementation
2023-04-13 11:55:40 -04:00
Cory LaViska
d3a0a38dce don't show hover when focused; fixes #1282 2023-04-13 10:31:24 -04:00
Cory LaViska
b76af1aa21 update changelog 2023-04-13 09:51:11 -04:00
Cory LaViska
5cf6a37ee2 wait until registered to set initial state; fixes #1292 2023-04-13 09:51:07 -04:00
Cory LaViska
63194abf93 prettier + changelog 2023-04-05 09:21:25 -05:00
Konnor Rogers
e196b0915a fix: split-panel divider now focusable in Edge / Chrome (#1289) 2023-04-05 09:18:57 -05:00
Cory LaViska
d2369d1de8 fix @since 2023-04-04 16:22:24 -05:00
dhellgartner
a9bbcc5556 first draft of testing guidelines (#1223)
Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-04-04 09:00:03 -05:00
Cory LaViska
8d9430e7a2 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-04-03 16:25:21 -05:00
Cory LaViska
0411754949 update changelog 2023-04-03 16:25:18 -05:00
Christophe Eymard
91ffaa1a2d stop holding a reference to a Promise when it is resolved (#1284) 2023-04-03 16:23:59 -05:00
Cory LaViska
ae9972a91a clarify events; #1283 2023-04-03 16:19:35 -05:00
Cory LaViska
478fa6f2bb update changelog 2023-03-31 15:03:31 -04:00
Cory LaViska
6a52a04591 Merge branch 'sloth30799-sloth30799' into next 2023-03-31 14:39:50 -04:00
Cory LaViska
a8f87e0d5e Merge branch 'sloth30799' of github.com:sloth30799/shoelace into sloth30799-sloth30799 2023-03-31 14:37:54 -04:00
Cory LaViska
cbc96fdf5c update changelog 2023-03-31 11:59:49 -04:00
dhellgartner
b4d24dd9af Added a basic test for animation (#1274)
Did not manage to check
that the properties are correctly passed
to the animation api at this point so this
stays a blackbox test

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-03-31 11:59:07 -04:00
Cory LaViska
4b66cc2acb update changelog 2023-03-31 11:53:43 -04:00
Thomas Blum
3766d5ce27 Fixed wrong property value (#1272) 2023-03-31 11:52:03 -04:00
Cory LaViska
4b7d686754 prettier + highlighter 2023-03-29 16:49:59 -04:00
gennitdev
b948a07a4d Include slot example for Vue (#1271) 2023-03-29 16:48:39 -04:00
Cory LaViska
6d3505aefa fix property name 2023-03-28 11:31:42 -04:00
Cory LaViska
b22650ff51 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-03-27 09:31:46 -04:00
Cory LaViska
23a7f65b49 fix variable name case 2023-03-27 09:31:43 -04:00
Han Ye Htun
f4fba8eab4 added tests 2023-03-24 00:05:10 +06:30
Christophe Eymard
1734bf54a7 replaced Set with WeakSet (#1249) 2023-03-23 12:13:13 -04:00
Cory LaViska
88efec7815 prettier 2023-03-23 08:39:20 -04:00
Marko Hrovatic
e335189bb8 Update angular.md (#1264)
Added an example how to access Shoelace components from component code
2023-03-22 16:39:20 -04:00
Han Ye Htun
d03ca4ab95 Avatar Initials visible when image has a transparent background(#1256) 2023-03-22 21:46:23 +06:30
Cory LaViska
257407758f remove unnecessary dep 2023-03-21 16:25:52 -04:00
Han Ye Htun
2443c046aa Avatar Initials visible when image has a transparent background(#1256) 2023-03-22 00:50:01 +06:30
Cory LaViska
d710eb3947 update changelog 2023-03-20 14:00:42 -04:00
dhellgartner
7b2f6f230d Added tests to the sl-animated-images component (#1246)
Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-03-20 13:59:54 -04:00
Cory LaViska
07cb6070cc Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-03-20 11:25:56 -04:00
Cory LaViska
bd7dc2a7be #1244 2023-03-20 11:25:55 -04:00
Alessandro
db931c12be fix: prevent expand button to shrink (#1245) 2023-03-20 11:24:58 -04:00
Cory LaViska
765b311a08 update changelog 2023-03-14 12:00:53 -04:00
Cory LaViska
ce198d9c0b Merge branch 'alenaksu-fix/tree-item/clickable-label-elements' into next 2023-03-14 11:59:06 -04:00
Cory LaViska
8f5893931b Merge branch 'fix/tree-item/clickable-label-elements' of github.com:alenaksu/shoelace into alenaksu-fix/tree-item/clickable-label-elements 2023-03-14 11:57:36 -04:00
Stefan Bauer
221be48589 fixed big bug typo ;-) (#1242) 2023-03-14 11:56:55 -04:00
Cory LaViska
234ff2619d fixes #1243 2023-03-14 11:16:39 -04:00
Alessandro
b37be46ba3 fix(tree-item): move label outside of checkbox 2023-03-13 19:52:12 +00:00
Cory LaViska
6e2ea508db update changelog 2023-03-13 11:48:35 -04:00
Jared White
0e6e2abd28 Export autoload discover function and support shadow roots (#1236)
* Export autoload discover function and support shadow roots

* run prettier
2023-03-13 11:47:37 -04:00
Cory LaViska
db1bdfbf65 update changelog 2023-03-13 10:58:01 -04:00
Alessandro
7bf0f647b3 fix(carousel): change the way slide position is computed (#1235) 2023-03-13 10:56:00 -04:00
Cory LaViska
44628889fe Merge branch 'next' into current 2023-03-09 16:23:15 -05:00
Cory LaViska
df25f8617b 2.3.0 2023-03-09 16:19:23 -05:00
Cory LaViska
ad2099a27f update version 2023-03-09 16:19:13 -05:00
Martin Alix
708127f96d Update French for Slide # (#1231) 2023-03-09 16:10:06 -05:00
Cory LaViska
9deb51e95a update docs 2023-03-09 16:09:33 -05:00
Cory LaViska
67852ea657 update installation docs 2023-03-07 16:52:02 -05:00
Cory LaViska
7240f4f8f4 Merge branch 'next' into autoload 2023-03-07 14:05:26 -05:00
Cory LaViska
17ee89a5e8 rename variable for clarity 2023-03-07 13:23:02 -05:00
Cory LaViska
f2177dccaf closes #1226 2023-03-07 11:03:03 -05:00
Cory LaViska
6aaf17b81a fixes #1224 2023-03-06 17:11:39 -05:00
dhellgartner
d113d13792 Fixed the avatar tests to produce less logs (#1222)
The reason for the problems is that the error event does
not escape from the shadow dom.
Thus it cannot be awaited for in the test

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-03-06 08:30:01 -05:00
Cory LaViska
ab9cb5f185 update changelog 2023-03-03 10:56:55 -05:00
Cory LaViska
76fd7aa28d trigger update immediately 2023-03-03 10:55:53 -05:00
Cory LaViska
8f17bf4e9d Improve Carousel Accessibility (#1218)
* fix demo

* improve accessibility, reorg, and polish up

* add support for up/down

* fix docs

* update docs
2023-03-03 10:53:17 -05:00
Cory LaViska
0f0f71af9b add custom-elements.json to exports 2023-03-03 10:36:30 -05:00
Cory LaViska
e624701022 fixes #1220 2023-03-03 10:16:15 -05:00
Cory LaViska
4cedfc3201 fix check 2023-03-02 11:43:09 -05:00
Cory LaViska
d88d9fc81a update example 2023-03-02 11:43:00 -05:00
Cory LaViska
051baa4ff5 remove warning 2023-03-02 11:27:47 -05:00
Cory LaViska
57c3d7009b fix example 2023-03-02 11:27:42 -05:00
Cory LaViska
a27fd4d2e9 Merge branch 'next' into autoload 2023-03-02 10:49:30 -05:00
Cory LaViska
79ac425e2b fix demo 2023-03-01 12:59:14 -05:00
Cory LaViska
857f318f9c fix overscroll (#1217) 2023-03-01 11:48:16 -05:00
Cory LaViska
c0966bf767 remove unused property 2023-03-01 11:35:25 -05:00
Cory LaViska
86cecc9e30 fix carousel pagination in iOS 2023-03-01 11:34:42 -05:00
Alessandro
ec036d8e61 fix(carousel): various fixes and improvements (#1216)
* fix(carousel): don't resume autoplay if interacting

* fix(carousel): wrap pagination items

* chore(carousel): add unit tests

* feat(carousel): more reactive pagination dots

* fix(carousel): trigger scrollend when user scroll exactly over a snap point
2023-03-01 11:05:29 -05:00
Cory LaViska
77b25f4581 add tag parts to <sl-select> 2023-03-01 10:58:24 -05:00
Cory LaViska
3168a1acf8 Merge branch 'next' into current 2023-02-28 17:11:30 -05:00
Cory LaViska
a8d59b3329 update changelog 2023-02-28 17:11:21 -05:00
Cory LaViska
17160e3bed Merge branch 'next' into current 2023-02-28 17:08:01 -05:00
Cory LaViska
5990fbd000 2.2.0 2023-02-28 17:05:11 -05:00
Cory LaViska
954d78dcd1 update version 2023-02-28 17:04:59 -05:00
Cory LaViska
3ea31389dd fixes #1082 2023-02-28 13:33:34 -05:00
Cory LaViska
d79799043a remove unused import 2023-02-28 13:07:18 -05:00
Cory LaViska
9f8ce58288 use clickOnElement 2023-02-28 13:07:07 -05:00
Cory LaViska
2371c5490f Merge branch 'next' into autoload 2023-02-28 12:45:23 -05:00
Cory LaViska
77abd42d66 fix popup positioning edge case; closes #1135 2023-02-28 12:30:05 -05:00
Cory LaViska
218e78e947 add getForm() method; closes #1180 2023-02-28 12:10:14 -05:00
Cory LaViska
8a1efac9b8 fixes #1201 2023-02-28 12:03:20 -05:00
Cory LaViska
f9ae8327f6 fix menu focus color 2023-02-28 09:46:49 -05:00
Cory LaViska
7f3076d195 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2023-02-27 16:40:55 -05:00
Cory LaViska
1fa79e64ae fix track color in dark mode 2023-02-27 16:40:53 -05:00
Bünyamin Eskiocak
dde1010465 Fixed clipped calendar toggle in Firefox (#1213)
* fixed clipped calendar toggle in firefox

* changelog

---------

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2023-02-27 12:04:32 -05:00
Cory LaViska
3a3a7347bc link to event 2023-02-27 11:15:57 -05:00
Cory LaViska
77c9750206 fix sl-tab-show event when closing 2023-02-27 11:13:59 -05:00
Cory LaViska
3d2e618be8 fix term 2023-02-24 16:08:06 -05:00
Cory LaViska
79feaae7fc adjust attribution 2023-02-24 15:56:31 -05:00
Cory LaViska
b0f7dfb86b update comment 2023-02-24 15:55:02 -05:00
Cory LaViska
e1979b8f38 reorder custom properties 2023-02-24 15:54:57 -05:00
Cory LaViska
7e9ae32b9b add carousel terms 2023-02-24 15:48:39 -05:00
Cory LaViska
480a1df246 reorder 2023-02-24 15:24:39 -05:00
Cory LaViska
ff798adb49 update examples 2023-02-24 15:10:54 -05:00
Cory LaViska
70a64262e9 add svg part 2023-02-24 12:51:46 -05:00
Cory LaViska
5f65896150 update localize 2023-02-24 12:35:25 -05:00
Cory LaViska
c69db4919b wip; improve carousel docs 2023-02-23 16:50:18 -05:00
Cory LaViska
a526e8a956 cleanup 2023-02-23 15:00:27 -05:00
Cory LaViska
4970ba065e set a default aspect ratio 2023-02-23 15:00:02 -05:00
Cory LaViska
0292ed30c5 update example 2023-02-23 14:59:48 -05:00
Cory LaViska
b64b1c2536 fix test 2023-02-23 14:49:49 -05:00
Cory LaViska
8f9eb012ba sort imports 2023-02-23 14:42:58 -05:00
Cory LaViska
c8fd9f19d2 ignore lorem ipsum 2023-02-23 14:40:05 -05:00
Cory LaViska
603aa93322 update and fix typos 2023-02-23 14:39:05 -05:00
Cory LaViska
74203de094 sort imports 2023-02-23 14:23:38 -05:00
Cory LaViska
4fa4682a45 Merge branch 'alenaksu-feat/carousel' into next 2023-02-23 14:20:01 -05:00
Cory LaViska
34e0fb2fc1 Merge branch 'feat/carousel' of github.com:alenaksu/shoelace into alenaksu-feat/carousel 2023-02-23 14:13:19 -05:00
Cory LaViska
50972f2b38 update changelog and comment 2023-02-23 11:33:31 -05:00
Cory LaViska
652ce6c9f1 Merge branch 'mpharoah-mpharoah/typescript-events' into next 2023-02-23 11:26:47 -05:00
Cory LaViska
8412b150b2 Merge branch 'mpharoah/typescript-events' of github.com:mpharoah/shoelace into mpharoah-mpharoah/typescript-events 2023-02-23 11:24:19 -05:00
Justin Fagnani
22b8ef4edf Fix a few spelling issues (#1192) 2023-02-23 11:15:20 -05:00
Cory LaViska
0865dede6f fix heading 2023-02-23 11:11:19 -05:00
Cory LaViska
d638d811ad remove unused type 2023-02-23 11:04:51 -05:00
Cory LaViska
bc58472b7b fix skipped tests 2023-02-23 11:02:26 -05:00
Cory LaViska
226c856b1e update scroll controls when adding tabs; fixes #1208 2023-02-23 10:12:36 -05:00
Cory LaViska
a127b8722e fix autoload timing issues 2023-02-22 14:18:43 -05:00
Cory LaViska
9c573fb454 add autoloader to docs 2023-02-22 14:18:36 -05:00
Cory LaViska
a346d18930 add autoloader docs 2023-02-22 14:18:19 -05:00
Cory LaViska
a32488baeb add autoloader prototype 2023-02-22 14:18:04 -05:00
Cory LaViska
a4131caeda add subpath 2023-02-22 14:16:11 -05:00
Cory LaViska
6c62a4f4c0 use passive listeners 2023-02-22 12:54:33 -05:00
Cory LaViska
5b12de1edf fixes #1205 2023-02-21 11:54:39 -05:00
Cory LaViska
f79a670ca3 fix padding in Chrome; closes #1197 2023-02-17 09:56:52 -05:00
Cory LaViska
fe2e2d6df5 Merge branch 'next' into current 2023-02-16 16:42:29 -05:00
Cory LaViska
e1ec60af62 2.1.0 2023-02-16 16:40:34 -05:00
Cory LaViska
dcbcc4c050 bump version 2023-02-16 16:39:11 -05:00
Cory LaViska
0eb3375bb9 welcome back, null 2023-02-16 16:30:13 -05:00
Cory LaViska
c26a8810c8 add crude inline error example; closes #1191 2023-02-16 16:22:46 -05:00
Cory LaViska
872227e345 reformat and add comment 2023-02-16 15:19:24 -05:00
dhellgartner
f22c529eab Avoid null logs on resize observer errors (#1196)
* Resize observer sometimes throws errors which
are nothing to worry about, see also the corresponding
comment on tab-group.test.ts
* Unfortunately, the web testing library installs an
error event handler which takes precedence before the
event handlers installed in the tests
(see node_modules/@web/browser-logs/dist/logUncaughtErrors.js)
* the only possibility to avoid these null logs is to install
an error event handler at an even earlier place

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-02-16 15:13:57 -05:00
dhellgartner
3430b33c3e Alert test (#1189)
* Improved tests for SlAlert

* added more test for coverage
* Grouped tests in multiple subgroups

* remove executing only one tests

* Fix the now executing tests

---------

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-02-16 15:04:11 -05:00
Cory LaViska
1bc2a6ef76 expose rel; fixes #1200 2023-02-16 12:15:59 -05:00
Cory LaViska
5a94f5bf5b update changelog 2023-02-16 10:43:28 -05:00
Thomas Blum
4277377189 Underscore was missing (#1195) 2023-02-16 10:39:01 -05:00
Matt Pharoah
d818980dea Fixed copy-paste type in comment 2023-02-15 09:41:05 -05:00
Matt Pharoah
636f61006f Adjusted comment to be more clear 2023-02-15 09:39:43 -05:00
Matt Pharoah
d93e698baf Added comments to explain the Typescript metaprogramming 2023-02-15 09:37:48 -05:00
Matt Pharoah
f8d8291caa Added sl-invalid event type 2023-02-14 23:06:47 -05:00
Matt Pharoah
21bef1c2ea Merge branch 'next' into mpharoah/typescript-events 2023-02-14 22:59:20 -05:00
Cory LaViska
f0efb9253c remove inline validation examples 2023-02-14 16:38:10 -05:00
Cory LaViska
cfd28f2608 update changelog 2023-02-14 15:24:19 -05:00
Cory LaViska
a3844fe074 comments 2023-02-14 15:21:52 -05:00
Cory LaViska
65e90f12f4 rename event 2023-02-14 15:12:21 -05:00
Cory LaViska
4335289d6a make doc comments consistent for check/report validity 2023-02-14 15:02:52 -05:00
Cory LaViska
86cc721e03 update description and document sl-invalid event 2023-02-14 14:59:34 -05:00
xdev1
4a28825ea7 Added some missing form validation standard features (implemented for #1181) (#1167)
* #1163 - added read-only properties 'validity' and 'validationMessage' to all nine form controls

* #1163 - added base support for showing form validation messages below the form controls

* #1163 - animated validation errors in demo

* #1181 - Removed all previous changes that have been validation error specific

* Started with 'Inline validation' demo / fixed merge issues / etc.

* #1181 - continued work on missing form validation features

* #1181 - enhanced validation support for SlColorPicker / some cleanup

* #1181 - fixed CSS issues

* #1181 - fixed again CSS issues

* '1181 - added form validation features finally working

* #1181 - bug fixes

* #1181 - fixed open issues / added API doc comments

* #1181 - updated inline validation demos / removed some legacy code

* #1181 - finished invalid form validation example

* #1181 - added tests / several bugfixes

* #1181 - fixed typos etc.

* #1181 - tests

* #1181 - tests

* #1181 - tests
2023-02-14 14:50:06 -05:00
Cory LaViska
19cf823da5 Merge branch 'ceymard-popup-element' into next 2023-02-14 09:30:47 -05:00
Christophe Eymard
737b55d78d allow Element as the anchor - now with correct typings 2023-02-10 21:56:57 +01:00
Cory LaViska
8493131db5 Revert "let popup be anchored to Element and not HTMLElement (#1186)"
This reverts commit 0d86c2af37.
2023-02-10 12:42:19 -05:00
Christophe Eymard
0d86c2af37 let popup be anchored to Element and not HTMLElement (#1186)
It works with SVG as well, is there a need to be restrictive here ?
2023-02-10 12:38:47 -05:00
Matt Pharoah
d6a7820a52 Make emit return the actual event type instead of CustomEvent<any> 2023-02-09 15:56:54 -05:00
Matt Pharoah
39ca1208f5 Removed unused event handler from sl-dropdown 2023-02-09 13:09:31 -05:00
Matt Pharoah
610a06bcb9 Use PropertyKey instead of string where appropriate 2023-02-09 13:06:17 -05:00
Matt Pharoah
b8584c0581 Require detail to always be provided when calling emit with an event that requires it 2023-02-09 13:00:04 -05:00
Matt Pharoah
ab19afeb66 Resolved merge conflict 2023-02-08 18:24:17 -05:00
Matt Pharoah
41b5cb367f Use typed events in components and tests 2023-02-08 18:19:27 -05:00
Matt Pharoah
e65b09fdec Fixed Typescript error when CustomEvents with non-object details are registered 2023-02-08 17:55:28 -05:00
Matt Pharoah
15a4049a01 Require the options parameter to have a detail property for events with details 2023-02-08 17:42:14 -05:00
Matt Pharoah
ce708fbba8 Perform type checking of the event detail in the emit function if the event type matches a Shoelace event 2023-02-08 17:01:00 -05:00
Matt Pharoah
75bd7784fb Basic events have an empty details object, not a null 2023-02-08 14:12:15 -05:00
Matt Pharoah
6e092ccf7a Added event types for all events 2023-02-08 13:55:19 -05:00
Matt Pharoah
b7b73ea3a9 Added sl-request-close event 2023-02-08 13:30:56 -05:00
Matt Pharoah
9dab91e0d1 Added event for sl-error 2023-02-08 13:17:12 -05:00
Matt Pharoah
a3a802a37b Register events with global event map 2023-02-08 13:14:43 -05:00
Matt Pharoah
358ad7bb30 Fixed type in documentation (TreeItem[] -> SlTreeItem[]) 2023-02-07 17:44:56 -05:00
Matt Pharoah
0a555c53c7 Export typescript types for events with details 2023-02-07 17:20:01 -05:00
Cory LaViska
b260a4dc29 add focus/blur to color picker 2023-02-07 17:18:03 -05:00
Cory LaViska
1f1024f4ca change default; #1175 2023-02-07 15:57:50 -05:00
Cory LaViska
9e92d92684 whitespace 2023-02-07 15:56:43 -05:00
Cory LaViska
527bf79973 improve user interaction heuristics; closes #1175 2023-02-07 15:29:26 -05:00
Cory LaViska
b281c5bbc1 use Set instead of WeakMap 2023-02-07 13:56:02 -05:00
Cory LaViska
f03de8925b fix checkbox required label in Chrome
See https://bugs.chromium.org/p/chromium/issues/detail?id=1413733
2023-02-07 10:52:54 -05:00
Cory LaViska
776ab2c715 add getForm() method 2023-02-07 09:01:32 -05:00
Cory LaViska
df967b7e84 improve checked state in forced-colors mode; fixes #1114 2023-02-06 18:00:39 -05:00
Cory LaViska
a539058253 validate even with novalidate; fixes #1164 2023-02-06 17:18:01 -05:00
Cory LaViska
af70d88153 improve icon page; fixes #1122 2023-02-06 15:19:08 -05:00
Cory LaViska
8dcffe270f remove 16.x from actions 2023-02-06 12:30:22 -05:00
Cory LaViska
c958f2e50a move focus logic; #1177 2023-02-06 12:20:32 -05:00
Cory LaViska
cedcd65c72 fix dropdown keyboard controls; closes #1177 2023-02-06 12:18:33 -05:00
Cory LaViska
12f62075ad move escape close logic to document listener; #1177 2023-02-06 11:32:06 -05:00
Cory LaViska
b8695b70a9 don't emit click when disabled; fixes #1113 2023-02-06 10:48:38 -05:00
Cory LaViska
a4e371618a fix comment 2023-02-06 10:47:08 -05:00
Cory LaViska
039ab175c3 add comment 2023-02-06 10:46:37 -05:00
Cory LaViska
7549e50fe4 fix positioning of native inputs; closes #1169 2023-02-05 12:06:06 -05:00
Cory LaViska
3c2cda699e fixes #1179 2023-02-05 11:08:57 -05:00
Cory LaViska
8685ddd049 fix select template; fixes #1178 2023-02-05 10:53:51 -05:00
Cory LaViska
c47ad40802 fixes #1172 2023-02-05 10:49:10 -05:00
Cory LaViska
ef1f129b22 fix test 2023-02-03 14:44:56 -05:00
Cory LaViska
6bb508ef14 revert; #1166 2023-02-03 14:36:17 -05:00
Cory LaViska
3596c8144d add dist to custom-elements.json; fixes #1166 2023-02-03 14:27:17 -05:00
Cory LaViska
20903bb638 update test 2023-02-02 12:23:32 -05:00
Alan Chambers
f45fb6848f Adjust sl-dropdown up/down keypress menuItems array to match menu (#1170)
* dropdown filtered menu items

* updated filter, added test

- updated filter to match menu getAllItems private method
- added test

---------

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2023-02-02 11:53:38 -05:00
Cory LaViska
400f9b76d5 ignore non-menu items; fixes #1165 2023-02-02 11:47:00 -05:00
dhellgartner
38a9e98d9b Tab group tests (#1128)
* remove duplicate test

* Add tests for sl-tab-group -- initial round of tests

* use individual fixtures for each test

* extract mocks + utility functions in external files

* remove unnecessary internals of intersection observer from the mock

* added first test on scroll buttons

* add scrolling tests

* remove resize observer mock

Resize observer is triggered but waiting for element
to be updated is not enough. You need to free the main thread
with the test for some time

* Also removed intersection observer mock

By waiting long enough for the things to happen automatically

* Fix problems with resize observer

These problems appeared after npm ci but (according
to the sources linked in the comments) unproblematic

* Handle merge request comments

* replace custom wait function with corresponding function
 from openwc/testing
* Extracted waitForScrollingToEnd and isElementVisibleFromScrolling into
dedicated files to be reused
* Improve queryByTestId --> make it usable for more complex values
* Add js docs

* run lint fix

* Added tests for selecting a tab by click

* added further tests for tab group selection

* use Promise<void> instead of Promise<any>

to avoid eslint errors

---------

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2023-01-27 09:55:28 -05:00
Cory LaViska
e8fe783fb4 fixes #1157 2023-01-26 14:22:04 -05:00
Cory LaViska
223ef32b70 fix web-types.json 2023-01-26 09:47:33 -05:00
Cory LaViska
0793a219a2 fix play/pause buttons; fixes #1147 2023-01-25 16:52:30 -05:00
Cory LaViska
6e2856db5f Revert "fix play/pause buttons; #1147"
This reverts commit 6d1eb71d8e.
2023-01-25 16:51:32 -05:00
Cory LaViska
6d1eb71d8e fix play/pause buttons; #1147 2023-01-25 16:51:02 -05:00
Cory LaViska
a334e53a5d Merge branch 'next' into current 2023-01-24 11:48:41 -05:00
Cory LaViska
3bb92c095f add state 2023-01-24 11:46:37 -05:00
Cory LaViska
deec097267 2.0.0 2023-01-24 11:43:38 -05:00
Cory LaViska
873e280700 update changelog 2023-01-24 11:38:17 -05:00
Cory LaViska
5d047f7a93 remove beta disclaimer 2023-01-23 12:55:45 -05:00
Cory LaViska
f24ab23752 add more design tokens to docs 2023-01-23 12:55:36 -05:00
Cory LaViska
44ecc8ce56 fixes #1141 2023-01-23 11:36:45 -05:00
Cory LaViska
e758b1d9bb whitespace 2023-01-23 11:29:50 -05:00
Cory LaViska
5cdbaa873d fixes #1141 2023-01-23 11:29:12 -05:00
Cory LaViska
e9aca6cedb fix part names; closes #1142 2023-01-23 10:51:24 -05:00
Cory LaViska
7c3896ed42 fix select input color; closes #1143 2023-01-23 10:44:19 -05:00
Cory LaViska
93158e8e90 fixes #1141 2023-01-22 13:34:32 -05:00
Cory LaViska
5f9bbdfa06 fixes #1139 2023-01-20 11:38:04 -05:00
Cory LaViska
3a0f486e98 fix label colors in checkbox, radio, and switch 2023-01-19 14:34:43 -05:00
Cory LaViska
29c671c0f4 fixes #1138 2023-01-19 14:22:29 -05:00
Cory LaViska
88c4bef5e7 Revert "Add JSON format for design tokens (#1129)"
This reverts commit 4a3f2caf59.
2023-01-19 11:37:52 -05:00
Cory LaViska
6066bc468b update config 2023-01-18 09:29:39 -05:00
Cory LaViska
efd944d822 remove contain:strict 2023-01-18 09:07:37 -05:00
Jared White
4a3f2caf59 Add JSON format for design tokens (#1129)
* Initial example of a JSON schema and converter for design tokens

* Clean up script and relocate file

* Update token JSON format and finish build process
2023-01-17 13:22:02 -05:00
Cory LaViska
511182b41b add padding to offset scrollbar; fixes #1132 2023-01-17 11:56:16 -05:00
Cory LaViska
1088a51ed5 fixes 1134 2023-01-17 10:45:19 -05:00
Cory LaViska
e3e0842bdd reorder importss 2023-01-17 10:44:07 -05:00
Cory LaViska
e4c908b08b add missing docs 2023-01-17 10:33:21 -05:00
Cory LaViska
f86578a213 fix tab panel display 2023-01-13 15:57:02 -05:00
Cory LaViska
3c2f5ec48e sort this, eslint 2023-01-13 15:43:55 -05:00
Cory LaViska
fec7ef17aa prettier 2023-01-13 14:42:21 -05:00
Cory LaViska
29ff99dd76 sigh 2023-01-13 14:37:45 -05:00
Cory LaViska
6b9b410bdc *put table back up* 2023-01-13 14:37:34 -05:00
Cory LaViska
b45a9d55ca update deps 2023-01-13 14:35:28 -05:00
Cory LaViska
7ce079b7a1 *flip table* 2023-01-13 14:29:25 -05:00
Cory LaViska
b0ba9ff14f remove expect 2023-01-13 14:22:45 -05:00
Cory LaViska
f665bf984b fix types 2023-01-13 14:22:06 -05:00
Cory LaViska
ac429a62c0 disable lint 2023-01-13 14:16:16 -05:00
Cory LaViska
dc909d10b6 fix words 2023-01-13 14:08:44 -05:00
Cory LaViska
aa65077b12 add getFormControls() method 2023-01-13 14:06:58 -05:00
Cory LaViska
7e37c51856 revert example 2023-01-13 12:52:02 -05:00
Cory LaViska
6e26daf804 add form attribute; fixes #1130 2023-01-13 12:34:33 -05:00
Cory LaViska
25c2d2d5bf upgrade CEM plugin 2023-01-13 10:39:59 -05:00
Cory LaViska
edc9e69f30 add @documentation tag 2023-01-12 10:26:25 -05:00
Cory LaViska
2e7ac38678 fixes #1127 2023-01-12 09:34:41 -05:00
Cory LaViska
1a68c825c0 update deps section 2023-01-11 15:29:51 -05:00
Cory LaViska
2cbdeeade0 remove cspell comment 2023-01-10 17:34:00 -05:00
Cory LaViska
79624f63ed add en-GB 2023-01-10 17:33:55 -05:00
xdev1
01a8ec36ec #1108 - simplification of translation files (#1120)
Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2023-01-10 17:33:23 -05:00
Jens Gabe
60324885ed Updated Danish translations (#1123)
Fixed typos and copy/paste translations from other languages
2023-01-10 17:30:01 -05:00
Cory LaViska
0c2f43b837 fixes #1125 2023-01-10 17:10:18 -05:00
Cory LaViska
0df27cf730 never return -0 2023-01-10 16:14:30 -05:00
Cory LaViska
68ed69292c add validation tests; fixes #1065 2023-01-10 15:05:44 -05:00
Cory LaViska
62c58b3a8c simplify validation logic 2023-01-10 15:05:07 -05:00
Cory LaViska
1fbb809057 update docs comment 2023-01-10 15:04:53 -05:00
Cory LaViska
e2d2f5d670 rename FormSubmitController; remove this.invalid 2023-01-10 13:24:06 -05:00
Cory LaViska
acef0da2c1 remove unused classes 2023-01-10 12:28:44 -05:00
Cory LaViska
3c66d2ab99 fixes #1121 2023-01-10 10:48:55 -05:00
Cory LaViska
31f16c4680 fix changelog 2023-01-09 16:31:05 -05:00
Cory LaViska
8056379fdd support multiple properties in watch decorator 2023-01-09 16:07:59 -05:00
Cory LaViska
9a6b9a7841 fixes #1119 2023-01-09 14:54:17 -05:00
Cory LaViska
02fc39ebe0 add parts 2023-01-09 14:25:26 -05:00
Cory LaViska
a90b22c05d add test 2023-01-09 14:25:21 -05:00
Cory LaViska
f5dd4f2aca fixes #1117 2023-01-09 14:20:17 -05:00
Cory LaViska
d5b3489b22 fixes #1066 2023-01-09 13:06:34 -05:00
Cory LaViska
8ee5f19184 pin source-map to beta; fixes #1066 2023-01-09 12:55:35 -05:00
Cory LaViska
d0a32d48b1 upgrade CEM and fix comment 2023-01-09 10:47:10 -05:00
Cory LaViska
bf527437a0 add stylesheet to test runner; fix tests 2023-01-09 10:35:37 -05:00
Cory LaViska
ae3070ac45 fixes #1107 2023-01-09 09:40:51 -05:00
Cory LaViska
6af68343a7 stop removing eslint comments 2023-01-09 09:39:47 -05:00
alenaksu
48ccc95dd9 chore: add react examples 2023-01-08 13:36:24 +01:00
Alessandro
c6a6a77bbd feat: add carousel component
feat: add nav indicators

wip

wip

wip

fix: minor fixes

fix: minor fixes

fix: some refactor

chore: update docs

chore: update docs

fix: remove slide component

feat: create sl-carousel-item

feat: code refactoring and improvements

chore: update docs with more examples

chore: fix docs

feat: add autoplay

feat: implement accessibility

fix: change icons for rtl

chore: minor change

feat: improve accessibility

fix: minor regression

fix: minor regression

chore: fix docs

fix: improve accessibility and minor fixes

fix: remove heading and refactor component

chore: add custom style exmaple

fix: address review commnets

* Removed header from carousel
* Added `ArrowUp` and `ArrowDown` in keyboard navigation
* Added `--scroll-hint-margin` css property
* Added an example with customized carousel layout
* Fixed thumbnails navigation in demo
* Renamed show-controls to show-arrows and updated the corresponding parts/css accordingly
* Changed `activeSlideElement` getter to a private method
* Changed pagination colors
* Added `--slide-width` and `--slide-height` css properties

chore: update docs

fix: integrate latest repo changes

fix: add aspect ratio and rebase

chore: remove ignore path

feat: multiple slides per page

feat: multiple slide per page

fix: various improvements

chore: minor changes

chore: minor changes

chore: add bit of documentation

chore: improve documentation

fix: add unit tests and fix minor issues

chore: update documentation and unit tests

chore: update tests
2023-01-08 12:24:24 +01:00
Cory LaViska
e632b51eb8 fixes #1110 2023-01-06 16:43:31 -05:00
Cory LaViska
c8e633c4a1 fix color picker bug 2023-01-06 15:24:57 -05:00
Cory LaViska
724f4a59db remove log 2023-01-06 13:28:48 -05:00
Cory LaViska
041364fb7d ignore swatch whitespace 2023-01-06 13:28:30 -05:00
Cory LaViska
fbcb4d8dbd fixes #1109 2023-01-06 12:25:03 -05:00
Cory LaViska
27a6b4a8c9 fixes #1108 2023-01-06 11:50:10 -05:00
Cory LaViska
0d50749ec8 Merge branch 'next' into current 2023-01-05 15:44:58 -05:00
Cory LaViska
c814e9e94e 2.0.0-beta.88 2023-01-05 15:43:08 -05:00
Cory LaViska
0e957c0cd4 update version 2023-01-05 15:41:32 -05:00
Cory LaViska
b330657e0a focus on disabled menu items and fix aria-checked 2023-01-05 15:13:21 -05:00
Cory LaViska
a0fce64fd9 closes #1070 2023-01-05 14:50:19 -05:00
Cory LaViska
b183a04fba add auto 2023-01-05 13:33:10 -05:00
Cory LaViska
7645b997b2 fixes #1105 2023-01-05 13:30:39 -05:00
Cory LaViska
d81e2f1470 fixes #1063 2023-01-05 12:43:17 -05:00
Cory LaViska
f50fe72df2 don't show scrollbar 2023-01-05 12:40:22 -05:00
Cory LaViska
dcca64a986 use public method for validity 2023-01-05 11:54:10 -05:00
Cory LaViska
c216cfe0fd fix min/max types 2023-01-05 11:29:51 -05:00
Cory LaViska
192f15e3b7 update cem plugin 2023-01-05 11:29:34 -05:00
Cory LaViska
01be3daf6d update docs 2023-01-04 14:51:30 -05:00
Cory LaViska
d36eec5637 add info about updateComplete 2023-01-04 14:04:24 -05:00
Cory LaViska
121464fa2d make swatches an attribute 2023-01-04 12:37:16 -05:00
Cory LaViska
ee0254e822 fixes #1097 2023-01-04 11:29:11 -05:00
Cory LaViska
27f634402c fix switch default value; #1103 2023-01-04 11:04:25 -05:00
Cory LaViska
67fbe3b34e fixes #1101 2023-01-04 09:58:56 -05:00
Cory LaViska
164ebce990 remove tts test 2023-01-03 15:17:39 -05:00
Cory LaViska
571ae704e0 update changelog 2023-01-03 15:10:51 -05:00
Cory LaViska
ad305fb653 Remove orphaned code 2023-01-03 15:09:57 -05:00
Cory LaViska
fc0541ce53 make internal 2023-01-03 15:08:49 -05:00
Cory LaViska
c8555f448c reorg and add private keyword 2023-01-03 15:04:07 -05:00
Cory LaViska
96e41198ec remove comment 2023-01-03 14:24:27 -05:00
Cory LaViska
57064aef4d remove void 2023-01-03 13:36:12 -05:00
Cory LaViska
cf200aa58a update tests 2023-01-03 10:37:39 -05:00
Cory LaViska
388a4f85a4 Revert "Remove the need to bind member methods in the connectedCallback (#1081)"
This reverts commit 5f8556b1b2.
2023-01-03 10:19:25 -05:00
Jeremiah Hoyet
5f8556b1b2 Remove the need to bind member methods in the connectedCallback (#1081)
* Remove the need to bind member methods in the connectedCallback

* Remove console.log
2023-01-03 10:15:12 -05:00
Cory LaViska
e411b57124 fixes #1096 2023-01-03 10:10:14 -05:00
Cory LaViska
0120e7429d update changelog 2023-01-03 09:49:56 -05:00
sowiner
377dbe28eb add zh-tw translations (#1086)
* add zh-tw translations

* add numOptionsSelected translate
2023-01-03 09:48:56 -05:00
Cory LaViska
b25b1d5750 Update changelog 2023-01-03 09:05:16 -05:00
Alan Chambers
0e1b792bf7 Update make-react.js script to use new @lit-labs/react createComponent options object (#1090)
* Update react wrapper signature

Updated react createComponent to use new options object

* removed unused pascalCase import
2023-01-03 08:57:27 -05:00
Cory LaViska
417f0d17c9 don't scroll when refocusing 2022-12-28 17:21:11 -05:00
Cory LaViska
d9252fe755 ignore disabled controls 2022-12-28 17:18:48 -05:00
Cory LaViska
c5555ab5fe Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-12-28 16:50:37 -05:00
Cory LaViska
eb61dc7d91 update bootstrap-icons 2022-12-28 16:50:35 -05:00
Bünyamin Eskiocak
a4c522f090 Added control--checked and control--indeterminate parts to <sl-checkbox> (#1085)
* removed checked and indeterminate parts from doc

* Revert "removed checked and indeterminate parts from doc"

This reverts commit 5e702387e1ace4e5d6b424f861df8e6a3a1a4fdd.

* control--checked & control--indeterminate parts
2022-12-28 16:40:59 -05:00
Cory LaViska
a8fe8c3e71 update hover styles 2022-12-28 16:36:07 -05:00
Cory LaViska
87000306c0 remove unused import 2022-12-28 16:25:33 -05:00
Cory LaViska
ae07b7d0a8 update changelog 2022-12-28 16:22:08 -05:00
Cory LaViska
626b76610f fix example 2022-12-28 16:22:05 -05:00
Cory LaViska
b4a1e1b0c9 fix docs 2022-12-28 16:12:41 -05:00
Cory LaViska
913243f8c1 more finishing touches + tests 2022-12-28 16:07:37 -05:00
Cory LaViska
563ed81984 remove example 2022-12-28 16:07:22 -05:00
Cory LaViska
fcbf339a86 remove unused selectors 2022-12-28 16:07:17 -05:00
Cory LaViska
70585e1d2a finishing touches 2022-12-28 15:31:42 -05:00
Cory LaViska
479e568296 update docs 2022-12-28 15:31:05 -05:00
Cory LaViska
a473e41ab3 fix docs 2022-12-28 14:43:01 -05:00
Cory LaViska
92f6a2d8e9 update changelog 2022-12-28 11:42:34 -05:00
Cory LaViska
06dc5740bf updates 2022-12-28 11:42:08 -05:00
Cory LaViska
fe524e0fac ignore clear button keys 2022-12-20 20:49:10 -05:00
Cory LaViska
ea7de2eb70 document slots 2022-12-20 18:44:57 -05:00
Cory LaViska
b8d02537a6 add grouping example 2022-12-20 18:44:33 -05:00
Cory LaViska
24744ef8c5 docs + cleanup wrapper 2022-12-20 18:24:25 -05:00
Cory LaViska
69997466be update example 2022-12-20 18:23:51 -05:00
Cory LaViska
f7d7fdf5b1 rerorder props 2022-12-20 18:23:19 -05:00
Cory LaViska
c0013c5639 refactor into set function 2022-12-20 17:53:55 -05:00
Cory LaViska
935040204f fix alignment to match other controls 2022-12-20 17:53:45 -05:00
Cory LaViska
2ffbf9b017 update examples 2022-12-20 17:43:50 -05:00
Cory LaViska
0f67b9a9d1 remove unused var 2022-12-20 13:51:53 -05:00
Cory LaViska
c5dee51233 restore example 2022-12-20 13:50:48 -05:00
Cory LaViska
b07238d536 temporarily disable a11y bug 2022-12-20 13:37:30 -05:00
Cory LaViska
e2a65c28f4 update select examples 2022-12-20 13:37:05 -05:00
Cory LaViska
1f457cdde0 keep on keepin on 2022-12-20 13:36:53 -05:00
Cory LaViska
46fda5f0a6 upgrade 2022-12-20 13:36:06 -05:00
Cory LaViska
e22c2f839b don't select disabled options 2022-12-20 13:00:27 -05:00
Cory LaViska
5bff912162 loosen up that type 2022-12-20 13:00:13 -05:00
Cory LaViska
f3010cecbe fix tests 2022-12-20 12:13:39 -05:00
Cory LaViska
2dc275defd fix validity and events 2022-12-20 11:40:49 -05:00
Cory LaViska
9f79445292 improve scroll on open 2022-12-20 10:31:55 -05:00
Cory LaViska
10cb26b81e focus after update 2022-12-20 10:21:41 -05:00
Cory LaViska
3722e0ad91 focus after open 2022-12-19 18:17:41 -05:00
Cory LaViska
f28a0ec743 fix in screen readers 2022-12-19 17:46:31 -05:00
Cory LaViska
a42b393bf1 Merge branch 'next' into select 2022-12-17 11:29:58 -05:00
Cory LaViska
41f50777bd update changelog 2022-12-17 11:29:25 -05:00
Cory LaViska
6afc3ba12e select rewrite (incomplete) 2022-12-17 11:27:30 -05:00
Alessandro
d8b7040a9e fix(tree): add initial sync (#1080) 2022-12-17 11:26:42 -05:00
Cory LaViska
316d8b52b6 Merge branch 'next' into current 2022-12-14 09:31:01 -05:00
Cory LaViska
59cd70ae6f 2.0.0-beta.87 2022-12-14 09:29:18 -05:00
Cory LaViska
6d9c8561fb update version 2022-12-14 09:22:57 -05:00
Cory LaViska
edb8a92838 update changelog 2022-12-14 09:22:30 -05:00
Cory LaViska
da3ffe9a60 update changelog and spelling list 2022-12-13 12:15:40 -05:00
Cory LaViska
e2b791dee8 i didn't attend Oxford, but I do like their commas 2022-12-13 12:15:28 -05:00
Alan Chambers
9178be576b color-picker library change and hsv format support (#1072)
* sl-color-picker use lib '@ctrl/tinycolor' instead of 'color'

typescript, esm and smaller

* parseColor adjustments

removed normalizeColorString and other tweaks

* added hsv format

* fixed const
2022-12-13 11:01:07 -05:00
Cory LaViska
752f5cff55 fixes #1071 2022-12-13 09:28:12 -05:00
Cory LaViska
3675787ddd remove polyfill 2022-12-13 07:24:06 -05:00
Cory LaViska
6284ed0347 Update tsconfig 2022-12-09 11:54:40 -05:00
Cory LaViska
1ff05c4b3d fixes #1061 2022-12-08 14:42:04 -05:00
Cory LaViska
066abe4e52 wait longer 2022-12-08 11:16:08 -05:00
Cory LaViska
e9134ddcf6 fixes #1051 2022-12-08 10:54:05 -05:00
Cory LaViska
0237851aa1 fix failing test 2022-12-08 09:01:33 -05:00
Cory LaViska
b7b2d9265a Merge branch 'next' into current 2022-12-08 08:53:20 -05:00
Cory LaViska
1841251fdf Current (#1059)
* Update fa.ts (#1053)

Improved translations by using original Farsi words rather than English ones

* Revert "Update fa.ts (#1053)" (#1058)

This reverts commit c951661b58.

Co-authored-by: Hadi F <62212402+hadi-f90@users.noreply.github.com>
2022-12-08 08:52:55 -05:00
Cory LaViska
b797803a2b Merge branch 'next' into current 2022-12-08 08:51:59 -05:00
Cory LaViska
b1e48406f3 #1053 2022-12-08 08:51:03 -05:00
Cory LaViska
bcb4f2267b Revert "Update fa.ts (#1053)" (#1058)
This reverts commit c951661b58.
2022-12-08 08:50:10 -05:00
Hadi F
c951661b58 Update fa.ts (#1053)
Improved translations by using original Farsi words rather than English ones
2022-12-08 08:45:07 -05:00
Cory LaViska
4ca51cf11e cleanup 2022-12-07 17:43:48 -05:00
Cory LaViska
41bd61c3a5 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-12-07 17:40:49 -05:00
Cory LaViska
c6df057e15 fixes #917 2022-12-07 17:40:46 -05:00
Alan Chambers
1428481a5c Add direct react export to package.json (#1050) 2022-12-07 09:23:26 -05:00
Cory LaViska
1c359fbea9 2.0.0-beta.86 2022-12-06 15:38:56 -05:00
Cory LaViska
0329694760 update version 2022-12-06 15:38:52 -05:00
Cory LaViska
936ec5a23a fix focus visible 2022-12-06 15:32:06 -05:00
Cory LaViska
d291506284 update docs 2022-12-06 14:12:36 -05:00
Cory LaViska
3877351fdc fix wrong values for buttons in form submission 2022-12-06 14:04:34 -05:00
Cory LaViska
7885572ebd jsdoc exported functions 2022-12-06 11:48:57 -05:00
Cory LaViska
2ee926023c fix translate arg 2022-12-06 11:41:51 -05:00
Cory LaViska
69e557cd8c convert to static method 2022-12-06 11:37:44 -05:00
Cory LaViska
f2efa73e20 improve documentation 2022-12-06 11:18:14 -05:00
Cory LaViska
2dd57956d5 move slots up and add parens to methods 2022-12-06 11:17:48 -05:00
Cory LaViska
ce86a1c9f2 update CEM plugin 2022-12-06 11:17:28 -05:00
Cory LaViska
a0f83c3b2b fix border radius bug 2022-12-05 09:38:42 -05:00
Cory LaViska
80a16ee42a remove slot wrappers 2022-12-02 17:03:59 -05:00
Cory LaViska
31b05fedd3 fix mislabeled slot 2022-12-01 16:39:39 -05:00
Cory LaViska
d3a7950483 add fallback content 2022-12-01 16:36:53 -05:00
Cory LaViska
f299621490 add note about icons + slots 2022-12-01 16:29:02 -05:00
Cory LaViska
c62ee3e207 refactor icon animation 2022-12-01 16:02:36 -05:00
Cory LaViska
a313087937 fix example 2022-12-01 16:01:45 -05:00
Cory LaViska
3945571b20 update changelog 2022-12-01 15:39:40 -05:00
Cory LaViska
c6a044416a remove transform from animations 2022-12-01 15:38:59 -05:00
Cory LaViska
d2f1b50ad0 fix tree item bug 2022-12-01 15:29:46 -05:00
Cory LaViska
1f1bae77dd don't use transform 2022-12-01 15:28:02 -05:00
Cory LaViska
829e22dc1e stop using transform 2022-12-01 15:26:46 -05:00
Cory LaViska
8b28ee818f improve custom icons 2022-12-01 15:25:09 -05:00
Cory LaViska
afb2e3d5b4 fix docs 2022-12-01 14:08:16 -05:00
Cory LaViska
fb0adb9ccb fix description 2022-12-01 13:28:04 -05:00
Cory LaViska
efea514f5a add summary-icon slot + example; #1046 2022-12-01 13:23:09 -05:00
Cory LaViska
fda9bd52a3 move up 2022-11-30 15:45:21 -05:00
Cory LaViska
01f8ce6b03 fix typo 2022-11-30 15:43:43 -05:00
Cory LaViska
e10651565f fix typos 2022-11-30 15:43:36 -05:00
Bünyamin Eskiocak
35aa56d334 Added title attribute (#1043)
* added title attribute

Fixes #1042

* added tests for title

* also some other tests

* clarify why title was added
2022-11-30 15:42:56 -05:00
Tao Cumplido
31e1f2fc59 fix sl-selection-change event not emitted when all items are deselected (#1038)
also added more tests
2022-11-30 08:18:56 -05:00
Cory LaViska
ee30f7a10b fix indicator animation bug 2022-11-29 16:06:52 -05:00
Cory LaViska
a50909d474 fixes #1037 2022-11-29 15:52:13 -05:00
Cory LaViska
63115d51e5 fixes #1036 2022-11-29 14:47:23 -05:00
Cory LaViska
026036a14b fix border when hovering over icon; #1035 2022-11-29 14:22:50 -05:00
Cory LaViska
22e09a778b update test to account for removed attrs 2022-11-29 11:30:11 -05:00
Cory LaViska
488088d5f0 add header-actions slot 2022-11-29 11:17:15 -05:00
Cory LaViska
0c18880e5c replace icon x => x-lg 2022-11-29 11:03:58 -05:00
Cory LaViska
0b0a571d17 update changelog 2022-11-29 10:01:53 -05:00
Cory LaViska
ea9e596279 remove unused attribs 2022-11-29 10:01:25 -05:00
Cory LaViska
fe17c8406b add link to BEM post 2022-11-29 09:47:48 -05:00
Cory LaViska
e7a4a5135d improve screen reader experience 2022-11-29 09:25:45 -05:00
Cory LaViska
ebf12860be update changelog 2022-11-28 16:17:43 -05:00
Bünyamin Eskiocak
4b81778e46 moved changelog entry to correct version (#1033) 2022-11-28 16:14:16 -05:00
Cory LaViska
28a8a90bb1 update docs 2022-11-28 16:13:36 -05:00
Cory LaViska
8dab5a8f04 Merge branch 'next' into cem-better-data 2022-11-28 16:07:29 -05:00
Cory LaViska
4ac9483213 remove unused config 2022-11-28 16:06:35 -05:00
Cory LaViska
ae3c0d72c0 update plugin 2022-11-28 16:05:11 -05:00
Cory LaViska
83b73e823d update changelog; #1030 2022-11-28 11:56:13 -05:00
Tao Cumplido
da6ae608f1 only emit a tree's selection change event when the selection has actually changed (#1030) 2022-11-28 11:55:12 -05:00
Cory LaViska
1e39647d7f Merge branch 'next' into cem-better-data 2022-11-28 11:51:20 -05:00
Cory LaViska
4dc92247d5 add usage disclaimer to popup 2022-11-28 09:56:41 -05:00
Cory LaViska
1b6f982d68 fix missing dist 2022-11-28 09:24:27 -05:00
Cory LaViska
81c775ea87 2.0.0-beta.85 2022-11-24 13:39:15 -05:00
Cory LaViska
09f741e930 update changelog 2022-11-24 13:36:21 -05:00
Tao Cumplido
602a863d89 fix isTreeItem method when called with non-element nodes (#1026) 2022-11-24 13:33:33 -05:00
Cory LaViska
3dd19a7f62 fixes #1024 2022-11-24 13:29:34 -05:00
Cory LaViska
bdf890ab0d Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-11-23 10:48:04 -05:00
Cory LaViska
0b7eae0c20 update changelog 2022-11-23 10:48:02 -05:00
Tao Cumplido
f3e273744a don't treat lazy tree items as leaf nodes (#1023) 2022-11-23 10:46:25 -05:00
Cory LaViska
7f9b0bd5a2 fixes #1024 2022-11-23 10:38:04 -05:00
Cory LaViska
6579a95999 fixes #1024 2022-11-23 10:32:27 -05:00
Cory LaViska
aaa8e4a01b 2.0.0-beta.84 2022-11-22 15:26:00 -05:00
Cory LaViska
200d4385ec update version 2022-11-22 15:23:57 -05:00
Cory LaViska
50d983a1ab move controls and show code when clicking 2022-11-22 15:06:11 -05:00
Cory LaViska
1e6d295746 update form validation docs 2022-11-22 14:18:54 -05:00
Cory LaViska
5d128c154c remove tab reuse logic
This broke recently so might as well remove the extra logic and make launching a bi faster.
2022-11-22 13:22:51 -05:00
Cory LaViska
6c7d7f4b7e revert dist 2022-11-22 13:01:15 -05:00
Cory LaViska
0cc8fdb8f8 add comment 2022-11-22 11:00:36 -05:00
Uilton Oliveira
4f7d915853 Fix mapping in exports (#1020)
* Fix mapping in exports

Fixes #1019
- Add correct mapping for public entrypoints.

* Remove shoelace.js from from exports list

Should still works fine while importing this way: import { thing } from '@shoelace-style/shoelace';
2022-11-22 10:58:07 -05:00
Cory LaViska
61738a3f6a update cem plugin 2022-11-22 09:23:10 -05:00
Cory LaViska
9061c1987a Merge branch 'next' into cem-better-data 2022-11-22 09:01:05 -05:00
Cory LaViska
c40b3a86a9 add support for extended language codes 2022-11-22 08:55:34 -05:00
Cory LaViska
8b2c090bac fixes #1018 2022-11-21 16:18:44 -05:00
Bünyamin Eskiocak
8f2a3bd8bd fixed type validation by changing variant to type (#1017) 2022-11-21 16:06:41 -05:00
Cory LaViska
ade05a6262 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-11-21 12:41:15 -05:00
Bünyamin Eskiocak
a706e69be6 Added stepUp, stepDown and showPicker functions (#1013)
* added stepUp and stepDown to sl-range

* step function & default props tests for sl-range

* stepUp, stepDown & showPicker functions for input

* step functions & default props tests for sl-input

* made name and placeholder default to empty string

* updated changelog

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2022-11-21 12:41:09 -05:00
Bünyamin Eskiocak
bc6a813c46 Added formenctype to <sl-button> (#1009)
* added formenctype to sl-button

* updated changelog

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2022-11-21 12:37:54 -05:00
Cory LaViska
599373c24a use attr not prop 2022-11-18 10:45:47 -05:00
Cory LaViska
daebd08475 add validation states to all form controls; closes #1011 2022-11-18 09:56:05 -05:00
Cory LaViska
a3f658938d bulletproof part selectors 2022-11-17 09:35:44 -05:00
Cory LaViska
23414fe411 fix callout 2022-11-16 14:59:35 -05:00
Cory LaViska
c8061fdee9 update deps 2022-11-16 14:57:21 -05:00
Cory LaViska
857b21a6a3 don't error out on missing summaries 2022-11-16 12:58:32 -05:00
Cory LaViska
48be3f46b8 add cem-custom-data-generator 2022-11-16 12:47:34 -05:00
Cory LaViska
66012a57c8 remove unused properties; #1007 2022-11-16 10:21:38 -05:00
Samuel Stroschein
0e77d8a459 add "exports" field to fix node16 module resolution (#1007) 2022-11-16 10:19:43 -05:00
Cory LaViska
b559c2345a remove whitespace 2022-11-15 13:52:03 -05:00
Cory LaViska
d79d7da299 various improvements in forced-colors mode 2022-11-14 16:12:24 -05:00
Cory LaViska
b296ac08cf fix menu selection in WHC 2022-11-14 14:49:48 -05:00
Cory LaViska
36e677dd6b fix dialog/drawer borders in WHC 2022-11-14 14:49:24 -05:00
Cory LaViska
6167993941 improve search in WHC 2022-11-14 14:49:13 -05:00
Cory LaViska
f9d3f0be27 use outline 2022-11-14 14:43:12 -05:00
Cory LaViska
7f76cacc10 make docs search usable 2022-11-14 14:41:35 -05:00
Cory LaViska
96cac8da85 improve color picker for WHC 2022-11-14 13:00:30 -05:00
Cory LaViska
a788e976c9 update docs/changelog 2022-11-14 09:50:35 -05:00
Emil
68c1319ed5 Add loading attribute to sl-avatar (#1006) 2022-11-14 09:48:26 -05:00
Cory LaViska
9db6f256e5 update icons 2022-11-14 09:11:12 -05:00
Cory LaViska
33e19c003c fixes #968 2022-11-10 17:12:29 -05:00
Cory LaViska
337d688bd3 add 18.x 2022-11-10 16:34:22 -05:00
Cory LaViska
cc305f8957 replace all paths in CEM 2022-11-10 16:27:23 -05:00
Cory LaViska
40cb38e0a0 point module paths to dist; fixes #725 2022-11-10 15:28:08 -05:00
Cory LaViska
a0d3ac047d loosen rule 2022-11-10 15:26:10 -05:00
Bünyamin Eskiocak
e399bd19a2 updated changelog (#1005) 2022-11-10 12:34:36 -05:00
Cory LaViska
f64f144b4b fixes #985 2022-11-10 12:27:03 -05:00
Cory LaViska
197a0c3048 update icon tests 2022-11-10 12:02:26 -05:00
Cory LaViska
e5e6b0d74f watch grouped tests by default 2022-11-10 11:43:40 -05:00
Cory LaViska
db1c2ee5cc update changelog 2022-11-10 11:30:51 -05:00
Cory LaViska
c6a43ba4c2 remove base from icons 2022-11-10 11:30:42 -05:00
Cory LaViska
ed45f52433 update comment 2022-11-10 08:06:35 -05:00
Cory LaViska
2d478c36fa fixes #963 2022-11-09 16:53:53 -05:00
Cory LaViska
f140007758 fixes #992 2022-11-09 16:07:34 -05:00
Cory LaViska
f03b09a410 fixes #965 2022-11-09 15:27:51 -05:00
Cory LaViska
0d9767596a disable rule 2022-11-09 13:18:05 -05:00
Cory LaViska
c626706e27 update changelog 2022-11-09 11:54:51 -05:00
VitaliyMaznyi
58b653f1ae improve input submit (#988)
add check to input component if japanese character is chosen by pressing enter key and prevent form submitting

Co-authored-by: VitaliyMaznyi <vitalii.maznyi@fasterthanlight.me>
2022-11-09 11:51:17 -05:00
Cory LaViska
5eeb98d39d fixes #925 2022-11-09 11:34:50 -05:00
Cory LaViska
e90b64b463 revert example 2022-11-09 09:58:04 -05:00
Cory LaViska
5fd682d83a fixes #990 2022-11-09 09:50:58 -05:00
Cory LaViska
49193c972f fixes #999 2022-11-08 12:15:14 -05:00
Cory LaViska
c027c0a527 use margin instead of padding 2022-11-07 12:31:13 -05:00
Cory LaViska
8160c33aa4 update deps 2022-11-07 12:06:34 -05:00
Cory LaViska
7d0226e3c4 make sl-show|hide cancelable 2022-11-03 10:33:10 -05:00
Cory LaViska
084c1dc5b5 fix tab a11y test 2022-11-02 08:48:39 -05:00
Cory LaViska
bfa320c5b5 fix a11y test 2022-11-02 08:43:52 -05:00
Buni48
4e1cf11461 Added turkish, british and austrian translations (#989)
* turkish translation

* austrian translation

* british translations

* updated changelog

* Update src/translations/en-gb.ts

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2022-11-02 08:37:22 -05:00
dhellgartner
5b4197da2c Relative time tests (#991)
* Added tests for sl-relative-time

* Solves a blinker which appears only when I run
the full test suite: Chromium and webkit are fine
but sometimes there is this one error on firefox
for the disabled test of the menu item (saying there
was a timeout waiting). Did not happen again after
doing the change.

Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2022-11-02 08:37:00 -05:00
Cory LaViska
e29b2f12fb fix typo 2022-10-28 11:16:12 -04:00
Cory LaViska
33a41bb2e4 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-10-28 09:57:44 -04:00
Cory LaViska
ab754e9409 add transition duration custom prop 2022-10-28 09:57:41 -04:00
dhellgartner
433955acf7 Added tests for sl-menu (#984)
Co-authored-by: Dominikus Hellgartner <dominikus.hellgartner@gmail.com>
2022-10-28 08:31:20 -04:00
Buni48
55445a80a3 removed left border from button group (#983) 2022-10-28 08:28:18 -04:00
Cory LaViska
9a64ea0670 update changelog 2022-10-27 13:00:17 -04:00
Buni48
0ff144a787 Fixed button group inner border disappears (#980)
* fixed button group inner border disappears

* updated changelog

* show border on active
2022-10-27 12:55:20 -04:00
bolte-17
8893045bf1 Avoid null dereference when removing event listeners in Dropdown (#958) 2022-10-27 09:28:35 -04:00
kzsa
a8de02bd53 Add hungarian translation (#982) 2022-10-27 09:21:20 -04:00
Michael Daross
4db0aec1c2 Fix: Issue 978 - Missing @summary annotation (#979)
Fixes https://github.com/shoelace-style/shoelace/issues/978
2022-10-27 09:20:19 -04:00
Cory LaViska
d885087c93 this is why we can't have nice thing 2022-10-24 10:45:42 -04:00
Cory LaViska
065aad2e4c bump node versions 2022-10-24 10:15:56 -04:00
Cory LaViska
9027ce055a prettier 2022-10-24 10:06:39 -04:00
Felix Becker
119b923522 testing: components/tag (#949)
* add test for SlTag

* add all classes (even not test relevant ones) to fix failing tests
2022-10-24 10:04:42 -04:00
Felix Becker
3b4d0652c4 testing: components/skeleton (#951)
* add tests for SlSkeleton

* check base aria-properties too
2022-10-24 10:04:30 -04:00
Felix Becker
1301934796 add test for SlRating (#953) 2022-10-24 10:04:17 -04:00
Emil
a8539bae02 Update vue-2.md (#959) 2022-10-24 10:03:24 -04:00
Manuel Schmidt
8121faa1d4 Enrich components @summary with description from docs (#962)
* keep header styles with repositioned description text

* `animated-image` move description to component

* code style

* `avatar` add summary from docs

* `badge` add summary from docs

* `breadcrumb` add summary from docs

* `button` add summary from docs

* lead sentence is now part of the header

* `button-group` add summary from docs

* `card` add summary from docs

* `checkbox` add summary from docs

* `color-picker` add summary from docs

* `details` add summary from docs

* `dialog` add summary from docs

* `divider` add summary from docs

* `drawer` add summary from docs

* `dropdown` add summary from docs

* `format-bytes` add summary from docs

* `format-date` add summary from docs

* `format-number` add summary from docs

* `icon` add summary from docs

* `icon-button` add summary from docs

* `image-comparer` add summary from docs

* `include` add summary from docs

* `input` add summary from docs

* `menu` add summary from docs

* `menu-item` add summary from docs

* `menu-label` add summary from docs

* `popup` add summary from docs

* `progressbar` add summary from docs

* `progress-ring` add summary from docs

* `radio` add summary from docs

* `radio-button` add summary from docs

* `range` add summary from docs

* `rating` add summary from docs

* `relative-time` add summary from docs

* `select` add summary from docs

* `skeleton` add summary from docs

* `spinner` add summary from docs

* `split-panel` add summary from docs

* `switch` add summary from docs

* `tab-group` add summary from docs

* `tag` add summary from docs

* `textarea` add summary from docs

* `tooltip` add summary from docs

* `visually-hidden` add summary from docs

* `animation` add summary from docs

* `breadcrumb-item` add summary from docs

* `mutation-observer` add summary from docs

* `radio-group` add summary from docs

* `resize-observer` add summary from docs

* `tab` add summary from docs

* `tab-panel` add summary from docs

* `tree` add summary from docs

* `tree-item` add summary from docs

* remove `title` for further usage of `Sl` classnames in docs

* revert: use markdown parser for component summary
2022-10-21 09:56:35 -04:00
Felix Becker
70766b4e68 add new theme token --sl-input-required-content-color to both themes (#948)
* add new theme token --sl-input-required-content-color to both themes

* use new token

* use label color as default value
2022-10-21 08:59:20 -04:00
Nick Cipriani
361efd43a2 Remove extra footer slot from Card with Footer example (#966)
The button and div both had a slot equal to footer when only the footer div actually needs it.
2022-10-21 08:08:49 -04:00
Manuel Schmidt
a78b9fe5bd sl-alert: move description from docs to component (#947)
* move component description from docs to component

* use component description in docs

* add style for lead sentence, keep bc for not updated components

* run `npm prettier`

* render summary as part of the header

* add `title` as another custom tag for JSDoc

* render components title in header
2022-10-19 09:35:53 -04:00
Manuel Schmidt
0cba4695ba Enrich docs with @summary and @title from custom-elements.json (#952)
* provide possibility to render components "description" into docs with `[component-description:COMPONENT_NAME]`

* the meta summary should be rendered into header too
2022-10-18 12:22:48 -04:00
Buni48
22fa81433e tests for sl-tab-panel (#956) 2022-10-18 10:49:50 -04:00
Buni48
5458a0e8f5 Added tests to menu-item & menu-label (#935)
* added tests to menu-item & menu-label

* updated changelog

* aTimeout instead of setTimeout
2022-10-14 08:55:09 -04:00
Buni48
0e67f85995 Fixed applying border radius to card header (#934)
* fixed applying border radius to card header

* updated changelog

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2022-10-14 08:36:11 -04:00
Buni48
808003f3df Added checked state part for radio & radio button (#933)
* added checked state part for radio & radio button

* updated changelog
2022-10-14 08:35:00 -04:00
Buni48
46c225d50f removed intl safari support notice (#954) 2022-10-14 08:34:11 -04:00
Cory LaViska
0a3656efc5 prettier 2022-10-03 16:19:22 -04:00
Greg Leaver
0aca600063 Fix <sl-range> docs to have correct closing tag in examples. (#928)
A couple of the examples had `</sl-input>` instead of `</sl-range>`
2022-10-03 16:15:04 -04:00
Cory LaViska
38f05ff010 ts 2022-09-21 10:30:23 -04:00
Cory LaViska
3d4cbbf6ba fix path 2022-09-21 10:27:37 -04:00
Cory LaViska
c877e16c14 improve badge font size 2022-09-20 10:25:01 -04:00
Cory LaViska
acce8eb146 increase badge padding 2022-09-20 10:19:35 -04:00
Cory LaViska
03fe71353a 2.0.0-beta.83 2022-09-19 08:50:51 -04:00
Cory LaViska
8915282082 update version 2022-09-19 08:46:31 -04:00
Cory LaViska
28003ac430 downgrade Floating UI for perf reasons 2022-09-19 08:39:11 -04:00
Cory LaViska
f2dcad82a9 fixes #916 2022-09-19 08:19:04 -04:00
Cory LaViska
69ff4f0bbc refactor emit into ShoelaceElement 2022-09-16 16:21:40 -04:00
Cory LaViska
a1c93fd30f fixes #913 2022-09-16 15:27:10 -04:00
ErikOnBike
bdf8c4e669 Fix workaround for Safari which still has old property name in sl-progress-ring (#914) 2022-09-16 15:14:38 -04:00
Cory LaViska
854e576c2c fixes #912 2022-09-16 15:11:02 -04:00
Cory LaViska
cf32064e8c add issue number 2022-09-12 08:53:32 -04:00
Cory LaViska
1f91d4cb79 add missing part 2022-09-12 08:50:16 -04:00
Cory LaViska
a7fdb23577 fix tooltip alignmen 2022-09-12 07:51:03 -04:00
Cory LaViska
39d1bbed2c fixes #905 2022-09-09 09:38:54 -04:00
Cory LaViska
e2e152c373 update changelog 2022-09-05 12:56:05 -04:00
Cory LaViska
aae74dbaf7 reorder and update changelog 2022-09-05 12:56:00 -04:00
Buni48
6c716db037 added expand button part for tree item (#893); fixes #890 2022-09-05 12:52:41 -04:00
Cory LaViska
7c0c0fa244 use event phase constants 2022-09-05 12:27:47 -04:00
Jared White
ffd32e52ef Avoid bubbling events for sl-include (#897)
* Avoid bubbling events for sl-include

I ran into an issue where icons inside of an HTML include were dispatching `sl-load` events, which was causing my `sl-include` event handler to run multiple times. By adding these guards, we ensure only events immediately dispatched by the element itself will be handled.

* Use the correct event variable
2022-09-05 12:23:47 -04:00
Cory LaViska
27868b56e8 fixes #891 2022-09-02 15:19:35 -04:00
Cory LaViska
346f13e5a5 fix arrow placement 2022-09-02 11:28:49 -04:00
Cory LaViska
69547d4800 remove unused styles 2022-08-31 16:19:42 -05:00
Patrick McElhaney
9fc4185f87 Better descriptions for checkbox attributes (#894)
The description for the checkbox's value attribute is currently "the checkbox's value attribute." I think we can do better than that, especially considering anyone who hasn't worked with old-school HTML forms that POST to the URL in the `action` attribute is unlikely to know why a checkbox has a value and that value is not boolean. 

While I was here I improved a couple of other descriptions. If there's an interest, I can expand this PR to update all of the properties in all controls where the description is tautological.
2022-08-31 16:14:34 -05:00
Justin Fagnani
08b5da7c56 Change LitElement and site to Lit and lit.dev (#889) 2022-08-30 23:28:45 -05:00
Cory LaViska
05e026876a fix transition in Firefox 2022-08-30 17:51:51 -05:00
Cory LaViska
8d0d0ac4e0 forEach 2022-08-30 16:59:40 -05:00
Cory LaViska
972d629883 remove 404 from search 2022-08-30 16:59:24 -05:00
Cory LaViska
ce12020fca remove clearable 2022-08-30 16:09:49 -05:00
Cory LaViska
29b149cd26 fix sidebar buttons 2022-08-30 16:08:51 -05:00
Cory LaViska
7de37b9315 remove date 2022-08-30 16:08:40 -05:00
Cory LaViska
237cda3b63 fixes #884 2022-08-30 11:56:34 -05:00
Cory LaViska
51c4abb72b remove log 2022-08-30 11:49:17 -05:00
Cory LaViska
3a6890af81 fixes #886 2022-08-30 09:17:46 -05:00
Cory LaViska
7cc2c89f92 remove responsive media 2022-08-26 10:43:12 -04:00
Cory LaViska
bb55c93b1a upgrade exp components 2022-08-26 10:33:45 -04:00
Cory LaViska
a3d00a92a0 fixes #882 2022-08-26 10:28:18 -04:00
Christian Oliff
5eccce625a Update node.js.yml (#883) 2022-08-26 09:46:35 -04:00
Cory LaViska
0c3a25d2ad prettier 2022-08-26 09:21:02 -04:00
Rich Klein
d225aaa2ff Update Laravel integration guide to reflect v9.1 (#865)
Laravel 9.1 now uses Vite as the default bundler instead of webpack.
2022-08-26 09:18:28 -04:00
Christian Oliff
c6b7c24ed7 Update .editorconfig (#880) 2022-08-26 09:16:57 -04:00
Cory LaViska
827c36bb1d update tree; fixes #879 2022-08-26 09:12:51 -04:00
Cory LaViska
d9f48a5f2a update examples 2022-08-26 09:11:09 -04:00
Cory LaViska
ccbdc6c014 fix docs 2022-08-25 17:36:06 -04:00
Cory LaViska
b6edba912b fixes #873 2022-08-25 17:22:18 -04:00
Cory LaViska
4cc5baaa0b fixes #876 2022-08-25 16:24:13 -04:00
Cory LaViska
c2bbb0e8a4 fix arrow 2022-08-25 16:09:27 -04:00
Cory LaViska
352cade421 fix example 2022-08-25 12:24:39 -04:00
Cory LaViska
708977acf7 2.0.0-beta.82 2022-08-25 10:03:51 -04:00
Cory LaViska
bab5749788 update version 2022-08-25 10:00:03 -04:00
Cory LaViska
c6d0b27f0d fix test 2022-08-25 09:46:34 -04:00
Cory LaViska
ee31f3f682 fix disabled tab tabbing 2022-08-25 09:42:55 -04:00
Cory LaViska
105bb08ee1 fixes #872 2022-08-25 09:37:20 -04:00
Cory LaViska
ca64d26d77 fixes #871 2022-08-25 09:18:36 -04:00
Cory LaViska
23b2f9335b add test for #869 2022-08-25 09:00:52 -04:00
Cory LaViska
dfdd7c75c2 fixes #869 2022-08-25 08:48:23 -04:00
Cory LaViska
156a2812ae fix docs 2022-08-25 08:33:32 -04:00
Cory LaViska
e42beab336 remove extra border and redundant styels 2022-08-24 15:08:32 -04:00
Cory LaViska
098db9c3fa add arrow-placement 2022-08-24 15:06:16 -04:00
Cory LaViska
81d393fbc1 update heroicons example to 2.0 2022-08-24 08:23:55 -04:00
Cory LaViska
2696b1a9ec fixes #867 (for real this time) 2022-08-23 10:55:49 -04:00
Cory LaViska
322f23ba56 revert fix 2022-08-23 10:42:16 -04:00
Cory LaViska
09224041b8 revert fix 2022-08-23 10:42:01 -04:00
Cory LaViska
326816e7b7 fixes #867 2022-08-23 09:00:03 -04:00
Cory LaViska
4117b6d219 fix fallback 2022-08-22 17:15:27 -04:00
Cory LaViska
af9905acff fix flip fallbacks and add example 2022-08-22 17:11:21 -04:00
Cory LaViska
e0727cc72c cleanup when auto-size changes 2022-08-19 14:32:53 -04:00
Cory LaViska
624297f624 update docs 2022-08-19 14:26:41 -04:00
Cory LaViska
1996037acc update auto-size; fixes #860 2022-08-19 14:21:30 -04:00
Cory LaViska
8fa665d3e7 fix react example 2022-08-19 10:26:16 -04:00
Cory LaViska
f0a3972ef6 add sync 2022-08-19 09:17:44 -04:00
Cory LaViska
c8f42c5bde fixes #862 2022-08-18 08:43:37 -04:00
Cory LaViska
7a6144d8c4 fix react example 2022-08-17 17:23:38 -04:00
Cory LaViska
ea71155b8f fix style types 2022-08-17 16:31:23 -04:00
Cory LaViska
20e9e3c320 tree updates 2022-08-17 16:22:03 -04:00
Cory LaViska
bcf2139fe7 fix types 2022-08-17 12:33:37 -04:00
Cory LaViska
48f864475e fix tree single select behavior 2022-08-17 12:33:33 -04:00
Cory LaViska
32f24a881e make dir/lang reactive everywhere 2022-08-17 11:37:37 -04:00
Cory LaViska
0163edd8a3 improve RTL 2022-08-17 10:48:40 -04:00
Cory LaViska
81620f0199 2.0.0-beta.81 2022-08-17 09:31:21 -04:00
Cory LaViska
d850b0f507 update changelog 2022-08-17 09:29:15 -04:00
Cory LaViska
19b2cde0d9 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-08-17 08:50:09 -04:00
Cory LaViska
87e252940d fixes #858 2022-08-17 08:50:07 -04:00
Cory LaViska
c6d30ae1b5 fix example 2022-08-16 15:32:14 -04:00
Cory LaViska
23bb45b1b6 add react example 2022-08-15 16:41:55 -04:00
Cory LaViska
70f59aa4ba add support for external anchors 2022-08-15 16:26:10 -04:00
Cory LaViska
237230961a fixes #854 2022-08-15 12:16:21 -04:00
Cory LaViska
b669ab7b74 fixes #855 2022-08-15 11:02:36 -04:00
Cory LaViska
040e8ce5e1 update deps 2022-08-11 09:59:02 -04:00
Denis Korablev
a74de59687 chore(i18n): fix ru translations (#853) 2022-08-11 09:27:10 -04:00
Cory LaViska
186f57cdde update docs 2022-08-11 09:22:35 -04:00
Cory LaViska
c94db27f07 fix rating a11y 2022-08-11 09:17:34 -04:00
Cory LaViska
578a58042b fix test 2022-08-10 16:53:27 -04:00
Cory LaViska
b3b3956ff5 improve spinner a11y 2022-08-10 16:52:39 -04:00
Cory LaViska
ce2abb97e0 accept cmd+k for search 2022-08-10 16:28:39 -04:00
Cory LaViska
6fc71601dd fix attribute 2022-08-10 16:25:27 -04:00
Cory LaViska
fd3da7e773 fix examples 2022-08-10 16:24:45 -04:00
Cory LaViska
70700b1ab5 fix example 2022-08-10 12:54:36 -04:00
Cory LaViska
eb9107bf2b add cursor 2022-08-10 11:31:30 -04:00
Cory LaViska
d0820178c9 remove background on hover 2022-08-10 11:12:07 -04:00
Cory LaViska
a8e8325ea7 fix popup 2022-08-10 11:01:13 -04:00
Cory LaViska
4b9e35313d remove dup 2022-08-10 09:13:50 -04:00
Cory LaViska
dc1394483a fix link 2022-08-10 08:29:49 -04:00
Cory LaViska
4b32b9461c 2.0.0-beta.80 2022-08-09 16:33:55 -04:00
Cory LaViska
308c8228aa fix tooltip 2022-08-09 16:29:55 -04:00
Cory LaViska
d74d2dec2e move var 2022-08-09 16:22:44 -04:00
Cory LaViska
c9f3497a8a update comment 2022-08-09 16:22:40 -04:00
Cory LaViska
8e57d0075c update version 2022-08-09 16:14:25 -04:00
Cory LaViska
73c8eba269 remove padding from example 2022-08-09 16:10:09 -04:00
Cory LaViska
1c0ffa7a24 fix changelog 2022-08-09 16:06:28 -04:00
Cory LaViska
014354efde fix typo 2022-08-09 16:01:33 -04:00
Cory LaViska
13ec55ba07 simplify initial open behavior 2022-08-09 16:01:13 -04:00
Cory LaViska
d6508a1262 fix initial open state and add test 2022-08-09 16:00:56 -04:00
Cory LaViska
9ebb5c8ec7 remove error 2022-08-09 16:00:43 -04:00
Cory LaViska
2093568981 use popup in dropdown 2022-08-09 15:28:01 -04:00
Cory LaViska
bd5ca9034c fix example 2022-08-09 15:27:41 -04:00
Cory LaViska
7ae454f8ca add data-current-placement 2022-08-09 15:27:34 -04:00
Cory LaViska
b9fcd09209 fix placement styles 2022-08-09 15:27:08 -04:00
Cory LaViska
cf2915a591 add react examples 2022-08-09 12:49:01 -04:00
Cory LaViska
9e625752be fix tag 2022-08-09 11:19:12 -04:00
Cory LaViska
147d1f048b update examples 2022-08-09 11:00:04 -04:00
Cory LaViska
801c4f70ec add examples 2022-08-09 10:52:36 -04:00
Cory LaViska
bcc9081247 update changelog 2022-08-09 10:52:31 -04:00
Cory LaViska
3919ea97e9 move it 2022-08-09 10:52:25 -04:00
Cory LaViska
876078b725 remove redundant style 2022-08-09 10:52:11 -04:00
Cory LaViska
c765a1df9b fix attrib names and middleware order 2022-08-09 10:52:04 -04:00
Cory LaViska
a1bc784bc7 bigger checks 2022-08-08 15:44:57 -04:00
Cory LaViska
d14b9e12ed use popup in tooltip 2022-08-08 15:41:19 -04:00
Cory LaViska
ab0fdd66b4 add sl-reposition event; support <slot> anchors 2022-08-08 15:40:21 -04:00
Cory LaViska
bf730f5bd2 use display:contents 2022-08-08 11:10:53 -04:00
Cory LaViska
8c667791fa fix menu item alignment 2022-08-08 11:08:13 -04:00
Cory LaViska
d07a8cfaea fix import paths 2022-08-08 10:15:41 -04:00
Cory LaViska
23deda2253 refactor watch logic 2022-08-08 10:08:57 -04:00
Cory LaViska
1c6cf769d4 update example 2022-08-08 10:08:53 -04:00
Cory LaViska
2add23d5d2 add example template 2022-08-05 16:13:24 -04:00
Cory LaViska
26693b2256 looking good; needs docs 2022-08-05 16:11:39 -04:00
Cory LaViska
f31d13c424 add popup 2022-08-05 09:17:58 -04:00
Cory LaViska
59182db564 reorder method 2022-08-04 09:22:13 -04:00
Cory LaViska
1bae224f80 remove constant 2022-08-04 09:17:08 -04:00
Cory LaViska
9b3240a14f update examples 2022-08-04 08:23:50 -04:00
Cory LaViska
860224c894 use token 2022-08-03 15:57:40 -04:00
Cory LaViska
a8b2eb2bb0 fix styles 2022-08-03 15:26:54 -04:00
Cory LaViska
cea69beca9 update radio group, radio, radio buton 2022-08-03 11:55:24 -04:00
Cory LaViska
4b7da8f510 update docs 2022-08-03 11:06:52 -04:00
Cory LaViska
6d31b1d63d remove unused styles; fix focus 2022-08-03 10:56:46 -04:00
Cory LaViska
7b55b38aa4 remove unused property 2022-08-03 10:56:37 -04:00
Cory LaViska
bf1121d126 Merge branch 'break-stuff-radio-group-a11y-fixes' into next 2022-08-03 10:00:49 -04:00
Burton Smith
fb2d419ab0 fix react example 2022-08-02 13:20:02 -04:00
Burton Smith
7179b60499 update docs 2022-08-02 13:16:19 -04:00
Burton Smith
ad00d8840e run prettier 2022-08-02 13:10:26 -04:00
Burton Smith
3d9fd3b889 disable button group role when nested 2022-08-02 13:03:47 -04:00
Burton Smith
90f4d77ed6 fix screen reader issues for radios and group 2022-08-02 12:59:00 -04:00
Cory LaViska
36d1e7c52e fixes #845 2022-08-02 08:26:03 -04:00
Andreas
2a1895a125 🔨 fix missing kbd closing tag (#846) 2022-08-02 07:51:00 -04:00
Cory LaViska
d5a352465e 2.0.0-beta.79 2022-08-01 12:18:57 -04:00
Cory LaViska
088ab99d02 revert version 2022-08-01 12:18:54 -04:00
Cory LaViska
42ed7f5cbb 2.0.0-beta.80 2022-08-01 12:17:16 -04:00
Cory LaViska
66e8259421 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-08-01 12:08:33 -04:00
Cory LaViska
1f34b63a2e revert radio fixes 2022-08-01 12:08:31 -04:00
Cory LaViska
cf3b4fa501 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-08-01 12:01:46 -04:00
Cory LaViska
73c190217f Revert "fix event docs"
This reverts commit f5bcd03c3f.
2022-08-01 12:01:34 -04:00
Cory LaViska
b2986e89b0 Revert "update changelog"
This reverts commit 8b2ddc984b.
2022-08-01 12:01:30 -04:00
Cory LaViska
2bf68e8a32 revert 2022-08-01 12:00:30 -04:00
Cory LaViska
f392ab4270 2.0.0-beta.79 2022-08-01 11:43:04 -04:00
Cory LaViska
eefb8f6a6b update version 2022-08-01 11:42:52 -04:00
Cory LaViska
8b2ddc984b update changelog 2022-08-01 11:41:56 -04:00
Cory LaViska
f5bcd03c3f fix event docs 2022-08-01 11:41:51 -04:00
Cory LaViska
92a73f21eb Merge branch 'fix-radio-a11y' of github.com:break-stuff/shoelace into next 2022-08-01 11:28:38 -04:00
Cory LaViska
4dbc3d2c8f Revert "fix checked handling"
This reverts commit 98746c86e4.
2022-08-01 11:25:09 -04:00
Burton Smith
90aac9abe9 fix type-o 2022-08-01 10:38:58 -04:00
Burton Smith
589021c40f remove logs 2022-08-01 10:38:07 -04:00
Burton Smith
1cc65b145a fix form validation 2022-08-01 10:35:00 -04:00
Cory LaViska
f6fbde3c96 update order 2022-08-01 10:34:50 -04:00
Cory LaViska
caf25773f0 Merge branch 'feat/tree-view' of github.com:alenaksu/shoelace into next 2022-08-01 10:21:53 -04:00
Alessandro
b904bb0736 chore: update styles 2022-08-01 13:58:24 +00:00
Cory LaViska
28ecc90e7f prettier 2022-08-01 09:28:47 -04:00
Cory LaViska
72fb9c7293 update changelog 2022-08-01 09:25:50 -04:00
Denis Korablev
d69712530c fix: fix dropdown hoist position (#844) 2022-08-01 09:24:11 -04:00
Alessandro
71a39600f5 chore: update docs 2022-08-01 12:51:14 +00:00
Alessandro
0291d7c28d chore: minor refactor 2022-08-01 12:48:02 +00:00
Alessandro
ed2417d974 feat: add customizable icons
* fix a bug focusing collapsed nodes
2022-08-01 12:41:36 +00:00
Burton Smith
85fd8a5204 update checked radio when value changes 2022-07-29 13:13:54 -04:00
Burton Smith
6446bb1013 prevent form submission 2022-07-29 12:31:29 -04:00
Burton Smith
2f8852245e update docs to reflect new API 2022-07-29 12:20:16 -04:00
Burton Smith
401b46bad8 update label 2022-07-29 12:20:00 -04:00
Burton Smith
ae3efaf8ae fix focus styles 2022-07-29 11:03:49 -04:00
Cory LaViska
98746c86e4 fix checked handling 2022-07-29 08:25:36 -04:00
Alessandro
268aef1711 fix: collapsed nodes are still focusable 2022-07-28 18:01:43 +00:00
Burton Smith
d765cef376 move validation logic and value to group level 2022-07-28 13:00:43 -04:00
Cory LaViska
23ed3d5647 add RTL info 2022-07-28 09:16:37 -04:00
Cory LaViska
1a7fbbfab4 fixes #839 2022-07-27 16:45:39 -04:00
Cory LaViska
47388d4a3f update deps 2022-07-27 16:17:23 -04:00
Cory LaViska
ce09869ea2 various updates 2022-07-26 15:53:24 -04:00
Cory LaViska
33587f51d3 Merge branch 'feat/tree-view' of github.com:alenaksu/shoelace into alenaksu-feat/tree-view 2022-07-26 08:17:41 -04:00
Cory LaViska
ed76d8aecc update changelog 2022-07-26 08:04:02 -04:00
Daniel Dennerkrans
33d2ec0597 added swedish translation (#838) 2022-07-26 08:03:02 -04:00
Alessandro
b4ae6ed1aa chore: update docs 2022-07-24 15:12:57 +00:00
Alessandro
b6839254d4 feat: add new tree-view component
feat: add indeterminate state

fix: rename item role

fix: aria attributes

fix: restore hover effect

fix: indeterminate state

chore: fix lint issue

fix: address (partially) review comment

fix: minor fix

feat: add keyboard navigation

fix: dependency name

fix: keyboard selection does not update all items

chore: minor changes

chore: remove leftover

chore: update documentation

feat: add lazy loading + several fixes

fix: add aria-busy attribute

fix: improve keyboard navigation and lazy loading

chore: fix linting issue

chore: minor fixes

fix: update component styling and slot

chore: remove exportparts attribute

fix: remove button margin for safari

fix: set correct part name

feat: implement selection modes and fix accessibility issues

chore: fix linting issues

chore: update docs

fix: minor fix

fix: treeitem height style

chore: update documentation

chore: refactor implementation

chore: implement unit tests

chore: update Enter key behavior

chore: update doc

chore: update doc
2022-07-23 15:16:17 +00:00
Cory LaViska
8ee811af58 fixes #837 2022-07-21 15:29:58 -04:00
Cory LaViska
f34ffdac55 fix color selection 2022-07-21 10:12:29 -04:00
Cory LaViska
d7e7ff6101 fix tooltip hoist position 2022-07-21 10:08:04 -04:00
Cory LaViska
1c36a7bcd4 remove void 2022-07-21 10:01:30 -04:00
Cory LaViska
7a77be017e improve menu a11y 2022-07-20 16:53:59 -04:00
Cory LaViska
5b5c6710fe add roles 2022-07-20 16:46:14 -04:00
Cory LaViska
04f7d2e182 use connectedCallback 2022-07-20 16:46:06 -04:00
Cory LaViska
36ee3c8a70 don't use getTarget() 2022-07-20 15:41:46 -04:00
Cory LaViska
98eec84422 fix tests 2022-07-20 15:37:47 -04:00
Burton Smith
bc08a4c005 run prettier 2022-07-20 15:34:10 -04:00
Cory LaViska
41580992f6 fix focus styles 2022-07-20 15:33:50 -04:00
Cory LaViska
9b7ce98ec0 fix disabled + focus styles 2022-07-20 15:32:26 -04:00
Cory LaViska
864d567572 improve tab accessibility 2022-07-20 15:29:19 -04:00
Burton Smith
cf360b3b3f fix radio a11y 2022-07-20 13:55:12 -04:00
Cory LaViska
673dc29dfe update changelog 2022-07-20 10:46:29 -04:00
Steven Traversi
849b643cfc Tooltip: Recalculate target after slotchange (#831)
* Tooltip: Recalculate target after slotchange

The tooltip's positioning breaks after a slotchange, unless the tooltips target is recalculated.

* Update src/components/tooltip/tooltip.test.ts

Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2022-07-20 10:43:47 -04:00
Cory LaViska
c39c4a9e9f update floating ui to 1.0.0 2022-07-20 08:28:16 -04:00
Cory LaViska
92c36c65cb update text 2022-07-19 09:39:51 -04:00
Cory LaViska
b6f25e09d2 fixes #815 2022-07-19 09:34:42 -04:00
Cory LaViska
71119c963d use classMap instead of inline style 2022-07-19 09:06:24 -04:00
Cory LaViska
ecf5ab5aad use classMap instead of inline style 2022-07-19 09:06:12 -04:00
Cory LaViska
7e581e6ad7 fix tab divider 2022-07-19 09:05:22 -04:00
Cory LaViska
36fa84e4b0 update changelog 2022-07-19 08:33:39 -04:00
Philipp Sonntag
3fb4cba856 Added type declaration to styles property for all components (#829)
* Updated the plop template with type for styles property
2022-07-19 08:27:39 -04:00
Cory LaViska
00f98cc505 update icon sprite 2022-07-18 08:41:48 -04:00
Cory LaViska
d9f719196a update bootstrap-icons 2022-07-18 08:18:01 -04:00
Cory LaViska
4b0c7245bd update sl localize 2022-07-15 12:16:43 -04:00
Cory LaViska
ced3a2a45a 2.0.0-beta.78 2022-07-15 10:00:20 -04:00
Cory LaViska
e6838e0a1f update version 2022-07-15 09:59:49 -04:00
Cory LaViska
9e637ce0db add shameless plug 2022-07-15 09:35:59 -04:00
Cory LaViska
acbee743a0 update deps 2022-07-14 09:11:16 -04:00
Cory LaViska
fa179fa30b fixes #824 2022-07-11 09:18:29 -04:00
Cory LaViska
2376f75f1d remove code blocks from search results 2022-07-11 09:13:57 -04:00
Cory LaViska
ca95822bba than than 2022-07-08 08:37:23 -04:00
Cory LaViska
6fbcd2158a add note about ai-generated code 2022-07-08 08:36:33 -04:00
Cory LaViska
389b78f748 remove :focus-visible shim 2022-07-07 09:43:27 -04:00
Cory LaViska
99368b9fdd fixes #821 2022-07-06 09:48:30 -04:00
Cory LaViska
a5a4621e25 update changelog 2022-07-06 08:39:11 -04:00
Cory LaViska
fe95ebaa95 Merge branch 'alenaksu-feat/range/active-track-offset' into next 2022-07-06 08:37:07 -04:00
Alessandro
01c7ca27fe feat(range): add active track offset 2022-07-06 09:27:37 +00:00
Cory LaViska
96ab3146be fixes #814 2022-07-05 08:58:11 -04:00
Cory LaViska
3c920cfed2 update text 2022-07-01 20:33:26 -04:00
Oliver Salzburg
db7caf1997 docs: Note that releases are not on a schedule (#810) 2022-07-01 20:25:24 -04:00
Oliver Salzburg
808815bdab docs: Fix duplicate package in list (#809) 2022-07-01 20:24:28 -04:00
Cory LaViska
8a8fd7f5a9 break it 2022-06-29 08:10:48 -04:00
Cory LaViska
3b3cb6d61d fixes #786 2022-06-29 08:09:25 -04:00
Cory LaViska
30a45f1d14 2.0.0-beta.77 2022-06-28 18:15:42 -04:00
Cory LaViska
d10f628f1d update version 2022-06-28 18:15:18 -04:00
Cory LaViska
615da18dc9 update changelog 2022-06-28 18:08:35 -04:00
Cory LaViska
be11c13f67 fix sort order 2022-06-28 18:08:28 -04:00
Cory LaViska
cb7f0aa41e webkit doesn't focus ranges like inputs 2022-06-28 18:01:55 -04:00
Alessandro
b2cf3a5505 feat(form): add reset functionality (#799)
* feat(form): add reset functionality

* feat(interal): add defaultValue decorator

* feat: add defaultValue and defaultChecked

* chore: implement unit tests

* chore: remove leftover
2022-06-28 17:59:52 -04:00
Cory LaViska
0d19c46d18 update changelog 2022-06-24 09:09:20 -04:00
Cory LaViska
c05832db67 Merge branch 'PavelDymkov-tabbable-fix' into next 2022-06-24 09:03:55 -04:00
Cory LaViska
e76dbef5f5 Merge branch 'tabbable-fix' of github.com:PavelDymkov/shoelace into PavelDymkov-tabbable-fix 2022-06-24 09:01:39 -04:00
Cory LaViska
25c00c80b7 fix label color 2022-06-24 08:46:44 -04:00
Pavel Dymkov
012206e4d8 Algorithm fix: fill "allElements" with only unique elements to improve performance. 2022-06-24 15:37:38 +03:00
Cory LaViska
de9da437f1 fix password autocomplete/correct/capitalize 2022-06-24 08:36:51 -04:00
Cory LaViska
153fe15ed3 fix label alignment 2022-06-24 08:22:13 -04:00
Cory LaViska
b58374aff1 fixes #798 2022-06-23 16:57:30 -04:00
Cory LaViska
31ae084538 fixes #797 2022-06-23 16:34:59 -04:00
Cory LaViska
f980126e81 fixes #796 2022-06-22 09:18:34 -04:00
Cory LaViska
cb1ada1bd7 Merge branch 'Buni48-next' into next 2022-06-22 09:03:10 -04:00
Cory LaViska
200d340123 Merge branch 'next' of github.com:Buni48/shoelace into Buni48-next 2022-06-22 08:57:36 -04:00
Buni48
5c2f4dd84e Revert "Fixes #791"
This reverts commit 1c23daa3b1.
2022-06-21 17:26:13 +02:00
Buni48
953d175b44 Revert "fixed typescript error"
This reverts commit 9549539f5d.
2022-06-21 17:25:13 +02:00
Buni48
f52a463728 merge next 2022-06-21 17:21:54 +02:00
Cory LaViska
5f25049abc fixes #791 2022-06-21 09:53:48 -04:00
Cory LaViska
8edaf67197 add checked-icon part 2022-06-21 09:37:16 -04:00
Cory LaViska
41c1979283 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-06-21 09:21:41 -04:00
Cory LaViska
9840891cdc update changelog 2022-06-21 09:21:36 -04:00
Cory LaViska
7d22e18bfb reflect fieldset and add required 2022-06-21 09:21:33 -04:00
Cory LaViska
07af6f2741 whitespace 2022-06-21 09:21:11 -04:00
Cory LaViska
60d9819088 add required symbol 2022-06-21 09:20:58 -04:00
Buni48
9549539f5d fixed typescript error 2022-06-19 19:40:50 +02:00
Buni48
1c23daa3b1 Fixes #791 2022-06-19 18:37:38 +02:00
Buni48
4a6c37ae0c Fixes #793 2022-06-19 18:22:52 +02:00
Oliver Salzburg
f1bfd58dd2 chore: Add missing colons (#792) 2022-06-18 17:13:03 -04:00
Cory LaViska
4446814114 2.0.0-beta.76 2022-06-15 09:27:32 -04:00
Cory LaViska
1ae6236e90 update version 2022-06-15 09:27:17 -04:00
Cory LaViska
624a8bbe71 fixes #777 2022-06-15 09:12:01 -04:00
Cory LaViska
ca876b291a revert formdata event detection 2022-06-10 17:22:34 -04:00
Cory LaViska
c850a7eae1 improve formdata event detection 2022-06-10 16:52:31 -04:00
Cory LaViska
5613a3cef3 upgrade localization lib 2022-06-10 16:37:10 -04:00
Cory LaViska
d3b161fc25 fix border bug 2022-06-10 09:44:27 -04:00
Cory LaViska
7659e45cc1 fix border bug 2022-06-10 09:44:22 -04:00
Cory LaViska
8a28d66393 fixes #784 2022-06-09 18:14:38 -04:00
Cory LaViska
c8d92e41b2 add link 2022-06-09 17:22:25 -04:00
Cory LaViska
9b39c90849 improve toast stack RTL styles 2022-06-09 17:21:44 -04:00
Cory LaViska
5c8a34696e revert dir 2022-06-09 09:24:11 -04:00
Cory LaViska
3e5da7c25a fixes #783 2022-06-09 09:23:33 -04:00
Cory LaViska
b1e6770712 2.0.0-beta.75 2022-06-08 17:24:52 -04:00
Cory LaViska
fd49fd6456 update version 2022-06-08 17:24:18 -04:00
Cory LaViska
d0ff2fef35 fix RTL in breadcrumb, tab group, and split panel 2022-06-08 17:15:40 -04:00
Cory LaViska
4c3313e275 improve badge RTL styles 2022-06-07 13:27:42 -04:00
Cory LaViska
4e0bc36b02 improve RTL in rating 2022-06-07 13:09:14 -04:00
Cory LaViska
01eb84e3a6 fix indeterminate state in RTL 2022-06-07 10:37:33 -04:00
Cory LaViska
70c97e2ae4 add --track-width; fix rtl 2022-06-07 10:26:04 -04:00
Cory LaViska
c165c8e71f update localize 2022-06-07 10:04:06 -04:00
Cory LaViska
6dd9773f2c update Floating UI 2022-06-07 09:27:15 -04:00
Cory LaViska
15dbb0a634 defer dom parser instantiation 2022-06-07 09:08:54 -04:00
Cory LaViska
ce09ac2a92 update base path 2022-06-07 08:59:29 -04:00
Cory LaViska
425f936254 fixes #781 2022-06-06 17:14:50 -04:00
Cory LaViska
7a9e4b0e8f fixes #776 2022-06-06 17:01:27 -04:00
xdev1
48f10011e1 Fixed translations for 'de' and 'de-CH' (#779) 2022-06-06 11:07:53 -04:00
Cory LaViska
f6d3f799dd update localize and fix range RTL 2022-06-06 10:57:59 -04:00
Cory LaViska
2157f4a385 update changelog 2022-06-02 08:17:12 -04:00
S. MohammadMahdi Zamanian
0f76d05546 add Persian translation
* feat: fa translate

* fix: fa localize name
2022-06-02 08:16:11 -04:00
Cory LaViska
293f49e178 fixes #775 2022-06-02 08:11:51 -04:00
Cory LaViska
4d2de2dd57 fixes #775 2022-06-02 08:10:46 -04:00
Cory LaViska
46dc965cd0 update changelog 2022-06-01 10:18:25 -04:00
Cory LaViska
707aeb6d65 revert button group RTL styles due to breakage 2022-06-01 10:17:36 -04:00
Godgiven
96c63c60a2 refactor: changed style to minimum support of RTL language (#768) 2022-06-01 10:00:46 -04:00
Cory LaViska
9539123fc3 improve image comparer icon 2022-06-01 09:36:16 -04:00
Cory LaViska
ea07346ae6 change weakmap name 2022-06-01 09:27:16 -04:00
Cory LaViska
af1e440103 fixes #772 2022-06-01 09:23:06 -04:00
Cory LaViska
0cea7d23f0 run prettier 2022-06-01 08:15:36 -04:00
Corbin Crutchley
ea8c88a31a docs: Update NextJS guide with ESM instructions (#771) 2022-06-01 07:43:39 -04:00
Cory LaViska
b4e5544ff8 fixes #767 2022-05-31 08:41:06 -04:00
Cory LaViska
04d534cd30 fixes #766 2022-05-31 08:31:41 -04:00
Cory LaViska
7cb247976f 2.0.0-beta.74 2022-05-27 15:06:45 -04:00
Cory LaViska
3cbf9e14e6 update version 2022-05-27 15:04:00 -04:00
Majid Valipour
3bd6516440 Fix broken link design tokens in docs (#733)
`light.styles.ts` no longer exists and has been replaced with `light.css`
2022-05-27 14:44:55 -04:00
Cory LaViska
e3f691fbda remove variant 2022-05-27 14:38:42 -04:00
Cory LaViska
ae76bea220 improve code block hover styles 2022-05-27 14:38:30 -04:00
Cory LaViska
ca81a507b6 rework focus rings 2022-05-27 10:13:51 -04:00
Cory LaViska
3f2382cfdc update vue instructions 2022-05-27 09:45:14 -04:00
Oleg Voronkovich
c1ccae315f Add instructions for Vue 3 (#756) 2022-05-27 09:41:47 -04:00
Cory LaViska
92cb4e3d29 move warning 2022-05-27 08:29:03 -04:00
Cory LaViska
9dd8c45c57 update deps 2022-05-27 08:23:02 -04:00
Cory LaViska
fa84a84a40 fixes #764 2022-05-27 08:15:31 -04:00
Cory LaViska
9e747e7c2e fixes #765 2022-05-27 07:43:42 -04:00
Cory LaViska
79306e0618 use HSB grid for color picker; fixes #762 2022-05-26 17:01:29 -04:00
Cory LaViska
139073dc3e fix word 2022-05-26 07:42:27 -04:00
Cory LaViska
18d441ef2e cache menu items 2022-05-25 09:53:19 -04:00
Cory LaViska
e07058ef5a add tablericons 2022-05-25 09:27:20 -04:00
Cory LaViska
f02941445b fixes #760 2022-05-25 08:56:22 -04:00
Cory LaViska
37b172dbfd fixes #758 2022-05-24 10:34:47 -04:00
Cory LaViska
4b2fc37015 update changelog 2022-05-24 09:00:34 -04:00
Cory LaViska
ae219c83fb fixes #743 2022-05-24 09:00:28 -04:00
Cory LaViska
e60c5c4546 update eslint 2022-05-24 08:12:13 -04:00
Cory LaViska
f57adb33eb update deps 2022-05-24 07:54:33 -04:00
Alan Chambers
25821c1294 Added datetime-local as valid sl-input type (#753) 2022-05-11 15:54:37 -04:00
Cory LaViska
8904e9d709 #744 2022-05-11 10:48:06 -04:00
Cory LaViska
35885ef59f fixes #744 2022-05-11 10:34:40 -04:00
Cory LaViska
c19eb5847a #751 2022-05-11 10:16:37 -04:00
Pavel Dymkov
c591f1d23e Fix error when set null or undefined to SlInput.value (#751) 2022-05-11 10:14:54 -04:00
Cory LaViska
fd1f76169a update changelog 2022-05-11 08:34:19 -04:00
Buni48
8814746738 Prevent toggling password & clearing on disabled form controls (#746)
* prevent toggling password & clearing on disabled form controls

* hide clear icon also on readonly
2022-05-11 08:33:27 -04:00
Cory LaViska
7bb6c4f0c1 update message 2022-05-11 08:27:00 -04:00
Cory LaViska
6c14282223 add base path note 2022-05-11 08:25:27 -04:00
Cory LaViska
7333760ada ignore polyfill types 2022-05-11 08:17:27 -04:00
Cory LaViska
cb0b5feef8 prettier 2022-05-11 08:12:02 -04:00
Cory LaViska
01369464fa Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-05-11 08:10:57 -04:00
Cory LaViska
c2ceaa9a3f update changelog 2022-05-11 08:10:56 -04:00
Cory LaViska
36716508c3 fix test type 2022-05-11 08:10:47 -04:00
Jared White
d683a76a49 Ensure FormDataPolyfill arg is optional (#749)
Fixes #747
2022-05-11 08:08:53 -04:00
Cory LaViska
4a0f6ef8af reflect disabled in dropdown 2022-05-02 16:33:30 -04:00
Cory LaViska
92b735b7fa update changelog 2022-05-02 16:28:21 -04:00
Buni48
240db01e75 reflecting name and library in sl-icon (#742) 2022-05-02 16:26:37 -04:00
Cory LaViska
04bacccfea use forEach instead of map; fixes #740 2022-05-02 07:48:43 -04:00
Cory LaViska
25b6e8c2d7 fix typo 2022-05-02 07:48:25 -04:00
Cory LaViska
1e2ceb8252 prettier 2022-04-26 08:13:13 -04:00
Buni48
329a5aec32 added time as valid sl-input type (#736) 2022-04-26 08:09:54 -04:00
Cory LaViska
c86ae623cb fixes #732 2022-04-25 08:00:16 -04:00
Cory LaViska
ce8dbc4302 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-04-19 09:30:20 -04:00
Cory LaViska
72972c76af fixes #730 2022-04-19 09:30:17 -04:00
modmuss50
d55813fffb Fix placeholder capitalisation (#731) 2022-04-19 08:55:00 -04:00
Cory LaViska
1f92e96079 add comma dangle rule 2022-04-15 09:28:09 -04:00
Cory LaViska
2cb3c1fc9f add env 2022-04-15 09:26:36 -04:00
Cory LaViska
caaf2b0d1e fixes #729 2022-04-14 18:01:25 -04:00
Cory LaViska
a635e4cd30 gtfo 2022-04-14 17:33:32 -04:00
Cory LaViska
aa336fb525 make touchstart passive 2022-04-14 16:58:08 -04:00
Cory LaViska
c0dc08116c remove unnecessary bind 2022-04-14 15:28:43 -04:00
Cory LaViska
a5b3334222 remove rules 2022-04-13 10:59:24 -04:00
Cory LaViska
8fd2491b9c use visually hidden tag 2022-04-13 10:29:27 -04:00
Cory LaViska
deea93acad 2.0.0-beta.73 2022-04-13 10:12:04 -04:00
Cory LaViska
ba92feee4a update version 2022-04-13 10:11:34 -04:00
Cory LaViska
e6458c26d6 fixes #727 2022-04-13 09:39:29 -04:00
Cory LaViska
4befbfafc5 improve tooltip a11y; #219 2022-04-13 09:02:23 -04:00
Cory LaViska
fc938ea3eb improve form control listeners 2022-04-11 10:36:16 -04:00
Cory LaViska
5e444a4f7c don't skip 2022-04-11 10:23:03 -04:00
Cory LaViska
1250627862 remove fix 2022-04-08 11:03:44 -04:00
Cory LaViska
a588bdc7b3 fix examples for codepen 2022-04-08 10:53:00 -04:00
Cory LaViska
44a4d13bad update note 2022-04-08 10:39:27 -04:00
Cory LaViska
7467806969 revert capturing due to inconsistent behavior; #718 2022-04-08 10:25:43 -04:00
Cory LaViska
9f844a8b91 fixes #718 2022-04-08 10:14:59 -04:00
Cory LaViska
83435a47de fixes #726 2022-04-08 08:56:05 -04:00
Cory LaViska
33612590ed fixes #720 2022-04-08 08:52:20 -04:00
James Garbutt
7475e9576c test: add image-comparer tests (#722) 2022-04-07 07:25:05 -04:00
James Garbutt
56d114f13d test: add tab tests (#724) 2022-04-07 07:24:59 -04:00
James Garbutt
50f702e9f1 test: add checkbox tests (#723) 2022-04-07 07:24:48 -04:00
Cory LaViska
43a361a52d update changelog 2022-04-06 10:12:06 -04:00
Cory LaViska
85976a1f35 use sendKeys/sendMouse 2022-04-06 09:48:54 -04:00
Cory LaViska
167cc6862a Merge branch '43081j-dropdown-without-menu' into next 2022-04-06 09:14:35 -04:00
Cory LaViska
5ca57e4110 Merge branch 'dropdown-without-menu' of https://github.com/43081j/shoelace into 43081j-dropdown-without-menu 2022-04-06 09:11:22 -04:00
Cory LaViska
988d09ed2a update test runner dep 2022-04-06 09:10:09 -04:00
Cory LaViska
bafa5fad54 stahp 2022-04-06 09:09:52 -04:00
43081j
a2e816253f fix (dropdown): tolerate dropdowns without menus 2022-04-05 20:08:54 +01:00
Cory LaViska
68603f9aed add enterkeyhint 2022-04-04 09:47:44 -04:00
Cory LaViska
46ac480713 update instructions 2022-03-30 09:13:49 -04:00
Cory LaViska
35cad794e9 update changelog 2022-03-30 09:07:51 -04:00
Cory LaViska
ee1a0c2c59 fixes #717 2022-03-30 09:05:19 -04:00
Cory LaViska
6f2ded4ce8 remove unused ts plugin 2022-03-28 09:03:19 -04:00
Cory LaViska
756b86a416 cycle through tabs/menu items 2022-03-24 08:50:44 -04:00
Cory LaViska
4b22fd2095 move to lint config 2022-03-24 08:23:58 -04:00
Cory LaViska
368854ba41 fix test 2022-03-24 08:17:28 -04:00
Cory LaViska
af4d25ee37 restore desired commits 2022-03-24 08:11:49 -04:00
Cory LaViska
cb460ee7ba test variants 2022-03-24 08:03:14 -04:00
Cory LaViska
300cbd090f revert path aliases 2022-03-24 08:01:09 -04:00
Cory LaViska
e32c15204c Revert recent changes 2022-03-24 07:48:03 -04:00
Cory LaViska
b8b68af316 update changelog 2022-03-23 17:38:07 -04:00
Cory LaViska
0a5fb5e9e7 refactor radio base class 2022-03-23 17:37:24 -04:00
Cory LaViska
99f475b56f remove comment 2022-03-23 17:37:11 -04:00
Cory LaViska
0b1ff75f1b add tests 2022-03-23 17:37:08 -04:00
Cory LaViska
ca653cd245 remove comment 2022-03-23 17:36:48 -04:00
Cory LaViska
84563bdcd4 update docs 2022-03-23 17:35:54 -04:00
Cory LaViska
49215503a6 add custom validity eexamples 2022-03-23 17:35:37 -04:00
Cory LaViska
9a8aafc189 remove tsconfig.prod 2022-03-23 17:35:11 -04:00
Cory LaViska
347808e86c test variants 2022-03-23 09:35:15 -04:00
Cory LaViska
f34960d82a revert path aliases since we can't override WTR's TS config 2022-03-23 09:30:39 -04:00
Cory LaViska
c6165ee502 pin TS 2022-03-22 11:11:10 -04:00
Cory LaViska
f676949460 remove unused import 2022-03-22 11:03:00 -04:00
Cory LaViska
73cfaee5ec fix typo 2022-03-22 10:59:20 -04:00
Cory LaViska
a6983d2d99 update styles 2022-03-22 10:56:34 -04:00
Cory LaViska
43e4a5b250 ts fixes 2022-03-22 10:32:39 -04:00
Cory LaViska
7b2c027c26 remove test 2022-03-22 10:32:28 -04:00
Michael Warren
e2069889b4 Icon and Icon-button tests (#706)
* initial button tests and setup helpers

* fix as many linting errors as I could

* switch back to regular fixtures

* test(button|button-group|divider|format-bytes) add tests for more components

* add tests for format util components

* finish format-number tests

* remove unnecessary ignore

* test(icon|icon-button) add tests for icon and icon-button

* chore(lint) fix linting issues

* chore(test) fix bad merge unintentional removes

* chore(test) remove unneded time el check

* chore(tests) fix PR comments

* chore(lint) lint rules

* chore(tests) fix missed accidental changes
2022-03-22 10:07:30 -04:00
Cory LaViska
499b3f1ff4 fixes #714 2022-03-21 08:51:41 -04:00
Cory LaViska
b4713f9bc6 fix typo 2022-03-20 09:18:32 -04:00
Cory LaViska
5132ee3559 fix react example 2022-03-19 18:24:37 -04:00
Cory LaViska
2a702d1cb5 add react example 2022-03-19 18:19:00 -04:00
Cory LaViska
23a4859e0e add color example 2022-03-19 18:14:37 -04:00
Cory LaViska
ae94aecdd7 2.0.0-beta.72 2022-03-18 17:34:05 -04:00
Cory LaViska
a6edf34a92 update changelog 2022-03-18 17:33:45 -04:00
Cory LaViska
c26b1335f5 refactor form control parts 2022-03-18 17:33:23 -04:00
Cory LaViska
fdeb7689d7 fixes #709 2022-03-18 16:02:58 -04:00
Cory LaViska
2d5e765193 add visually hidden dep 2022-03-18 15:58:35 -04:00
Cory LaViska
29d82736a7 update docs 2022-03-18 15:58:25 -04:00
Cory LaViska
e493c65b12 revert link cols 2022-03-17 10:53:03 -04:00
Cory LaViska
ada6f533b7 add label to color picker 2022-03-17 10:31:29 -04:00
Cory LaViska
5ea578b8c8 remove redundant attribs 2022-03-17 10:00:49 -04:00
Cory LaViska
67cb6abe56 update changelog 2022-03-17 09:49:49 -04:00
Cory LaViska
3ff6a02391 fix tag button 2022-03-17 09:48:08 -04:00
Cory LaViska
dde83e7f67 update images 2022-03-17 09:47:25 -04:00
Cory LaViska
fe527ff5dd Revert "improve constrast to meet AA standard"
This reverts commit ad0ac34f9d.
2022-03-17 08:33:11 -04:00
Cory LaViska
4f99bbace9 fix tests 2022-03-16 17:52:30 -04:00
Cory LaViska
ad0ac34f9d improve constrast to meet AA standard 2022-03-16 17:45:06 -04:00
Cory LaViska
ba3306b497 improve accessibility in various examples 2022-03-16 17:44:40 -04:00
Cory LaViska
7ff8b34e80 fix accessible trigger 2022-03-16 17:40:31 -04:00
Cory LaViska
fc4b1464b9 use time element in output 2022-03-16 17:40:08 -04:00
Cory LaViska
485347e20b use class for selector 2022-03-16 17:39:53 -04:00
Cory LaViska
34676105a1 hide helper buttons from readers 2022-03-16 17:39:39 -04:00
Cory LaViska
339eacb01f remove unused stylesheet 2022-03-16 17:39:09 -04:00
Cory LaViska
27a047976b fix disable aria 2022-03-16 17:38:58 -04:00
Cory LaViska
3289129782 ignore visually hidden when detecting slots 2022-03-16 17:37:42 -04:00
Cory LaViska
afa715c860 improve docs search a11y 2022-03-16 17:36:39 -04:00
Cory LaViska
ae0eddfb25 fix docs 2022-03-16 10:42:01 -04:00
Cory LaViska
13b2f8018d remove sl-error payload 2022-03-16 09:04:35 -04:00
Cory LaViska
eb66ce2d4b add watch flag to test:component 2022-03-16 08:57:25 -04:00
Cory LaViska
ad16b0b5a6 fix docs 2022-03-15 18:06:01 -04:00
Cory LaViska
c81f519b7c improve constrast in the docs 2022-03-15 18:01:01 -04:00
Cory LaViska
6450c0bee6 add radio button; refactor radio group 2022-03-15 17:42:59 -04:00
Cory LaViska
87d1db760f improve search results 2022-03-15 08:56:08 -04:00
Cory LaViska
1c903f4d26 refactor radio logic 2022-03-14 17:47:02 -04:00
Cory LaViska
b84a8bc76a fixes #704 2022-03-14 10:11:55 -04:00
Cory LaViska
e77f059685 revert example 2022-03-14 09:05:26 -04:00
Cory LaViska
4e108d434a fix tagToTitle helper 2022-03-14 08:59:21 -04:00
Cory LaViska
0f626bebbf upgrade visually hidden 2022-03-14 08:50:25 -04:00
Cory LaViska
cff57b6562 fixes #703 2022-03-11 14:31:25 -05:00
Cory LaViska
5cb9212fa4 update examples 2022-03-11 11:40:34 -05:00
Cory LaViska
c2910d742a fix form submission 2022-03-11 11:28:34 -05:00
Cory LaViska
e8174f7462 group tests 2022-03-11 11:27:36 -05:00
Cory LaViska
f245d97fc0 fix types 2022-03-11 09:26:19 -05:00
Cory LaViska
469c03f5e7 prettier + tag fix 2022-03-11 09:14:17 -05:00
Michael Warren
3144c45688 Button tests (#667)
* initial button tests and setup helpers

* fix as many linting errors as I could

* switch back to regular fixtures

* test(button|button-group|divider|format-bytes) add tests for more components

* add tests for format util components

* finish format-number tests

* remove unnecessary ignore
2022-03-11 08:56:24 -05:00
Cory LaViska
99e746ba81 2.0.0-beta.71 2022-03-09 16:56:59 -05:00
Cory LaViska
7527b9f9b1 update version 2022-03-09 16:56:47 -05:00
Cory LaViska
5e6add724d fix home and end in dropdown 2022-03-09 16:07:11 -05:00
Cory LaViska
a5cd9a4968 refactor parts and exported parts 2022-03-09 15:54:18 -05:00
Cory LaViska
c5fe481c33 update template 2022-03-09 09:51:20 -05:00
Cory LaViska
38b0ace0ca remove comments 2022-03-09 09:20:22 -05:00
Cory LaViska
1819f38ccb fix import order 2022-03-09 09:18:43 -05:00
Cory LaViska
4834ecbddb remove borders 2022-03-09 09:05:55 -05:00
Cory LaViska
3aa5fdba55 improve form controls a11y; add tests 2022-03-08 17:34:17 -05:00
Cory LaViska
8ae987ea69 update typeToSelect arg 2022-03-04 10:12:05 -05:00
Cory LaViska
d77f543c8f fix menu styles 2022-03-04 10:08:59 -05:00
Cory LaViska
517415f743 menu improvements 2022-03-03 17:15:58 -05:00
Cory LaViska
b9770e7e73 replace popper with floating ui 2022-03-03 15:48:20 -05:00
Cory LaViska
93cb8a2411 update eslint sorting 2022-03-02 17:20:40 -05:00
Cory LaViska
4866d2d190 fix valueAsDate and valueAsNumber bug 2022-03-02 12:19:59 -05:00
Cory LaViska
80a9d05ff3 add prettier and eslint to markdown 2022-03-02 10:10:41 -05:00
Cory LaViska
1db7aa3f26 remove overflow hidden 2022-03-02 09:46:11 -05:00
Cory LaViska
ff1e11022d reintroduce path aliasing and fix autosort 2022-03-02 09:28:34 -05:00
Cory LaViska
b55bf31fdc remove import sorter 2022-03-01 18:06:11 -05:00
Cory LaViska
75c557ec63 add group test shortcut 2022-03-01 18:06:05 -05:00
Cory LaViska
2116ba19f6 ignore modifier keys when pressing enter 2022-03-01 10:34:59 -05:00
Cory LaViska
8b9375ea68 fixes #700 2022-03-01 10:24:57 -05:00
Cory LaViska
9a024c6146 update docs 2022-03-01 09:32:01 -05:00
Cory LaViska
642de684e8 fixes #699 2022-02-28 09:59:32 -05:00
Cory LaViska
eb18d759f1 fixes #693 2022-02-27 11:46:55 -05:00
Cory LaViska
3fa41ea8d9 revert path aliasing and update import orders 2022-02-26 10:48:56 -05:00
Cory LaViska
1147d6ba4a add descriptions 2022-02-26 10:46:25 -05:00
Cory LaViska
b0bebcd162 2.0.0-beta.70 2022-02-25 10:06:44 -05:00
Cory LaViska
12dedf2047 update changelog 2022-02-25 10:06:17 -05:00
Cory LaViska
9af8184221 update changelog 2022-02-25 09:18:46 -05:00
Cory LaViska
62eeb06abe remove ga 2022-02-25 09:13:26 -05:00
Cory LaViska
e60b5f670a update changelog 2022-02-22 09:12:43 -05:00
Cory LaViska
6b2e64ef96 update comment 2022-02-22 09:12:39 -05:00
Denis Korablev
d6bfc773de fix positioning of active tab indicator (#695) 2022-02-22 09:10:33 -05:00
Cory LaViska
a1e4b50b29 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2022-02-21 09:13:40 -05:00
Cory LaViska
38c8762f64 update changelog 2022-02-21 09:13:37 -05:00
Cory LaViska
ddd5b581fa update docs 2022-02-21 09:13:33 -05:00
Patrick Nærvig Wøhlk
e2afe4b787 Add danish translation (#690) 2022-02-21 09:12:15 -05:00
Buni48
b24ff33fe0 Added placement property to sl-select (#687)
* added placement to sl-select

* sl-select placement: just allow top and bottom
2022-02-21 09:04:21 -05:00
Cory LaViska
0922ee202a update docs 2022-02-20 21:43:45 -05:00
Cory LaViska
946fcf2b25 add support for autofocus in dialog/drawer 2022-02-20 21:38:45 -05:00
Cory LaViska
a517a8038f fixes #688 2022-02-20 21:18:26 -05:00
Cory LaViska
faca17ff78 remove preventScroll option in fallback conditional 2022-02-20 21:05:07 -05:00
Cory LaViska
d4e6126ec3 fix changelog 2022-02-19 13:49:45 -05:00
Cory LaViska
5c0da06d66 add parts to select 2022-02-19 12:47:13 -05:00
Cory LaViska
0d3bcb0b2c improve tag remove button 2022-02-19 12:23:16 -05:00
Cory LaViska
e0ab8fc8e2 fixes #684 2022-02-19 11:56:16 -05:00
Cory LaViska
011f12a7e4 fixes #684 2022-02-19 11:56:09 -05:00
Cory LaViska
f7f146df04 2.0.0-beta.69 2022-02-16 16:15:08 -05:00
Cory LaViska
803a6d8a25 bump version 2022-02-16 16:14:51 -05:00
Cory LaViska
fa907a7f2b update deps + changelog 2022-02-16 16:13:54 -05:00
Cory LaViska
033a3a9db9 finishing touches 2022-02-16 16:02:21 -05:00
Matthias Guth
4a0dbde6b7 Customelements to webtypes (#681)
* (feat) generate web-types.json

* (feat) added doc ref

Co-authored-by: Matthias Guth <matthias.guth@vitagroup.ag>
2022-02-16 15:51:44 -05:00
Cory LaViska
e41e08f2af remove unused helper 2022-02-15 08:23:33 -05:00
Cory LaViska
c738f715a3 fixes #674 2022-02-14 18:15:45 -05:00
Cory LaViska
0d2572d37d updated changelog 2022-02-14 11:10:20 -05:00
Jake Patterson
a0df846493 issue 662 (#672) 2022-02-14 11:08:26 -05:00
Cory LaViska
01a6d60890 update changelog 2022-02-13 16:53:19 -05:00
Cory LaViska
8721999a22 fix typo 2022-02-13 16:53:13 -05:00
Jake Patterson
2b505466ce fix: tab group indicator offset when element is animated (#671)
* fix issue 622

* run prettier
2022-02-13 16:50:11 -05:00
Cory LaViska
17627d0775 update docs 2022-02-12 13:46:27 -05:00
Cory LaViska
0f87fb86a9 improve up/down logic in dropdown 2022-02-12 13:37:55 -05:00
Cory LaViska
f438f5252e 2.0.0-beta.68 2022-02-12 12:33:49 -05:00
Cory LaViska
a7291046a6 update changelog 2022-02-12 12:29:12 -05:00
Cory LaViska
9e15209161 Merge branch 'CreativeTechGuy-typescript-transform-paths' into next 2022-02-12 12:25:51 -05:00
Jason O'Neill
aed26b526a fix typescript path alias in declarations 2022-02-11 10:12:49 -08:00
Cory LaViska
da5b7afa58 2.0.0-beta.67 2022-02-11 08:26:35 -05:00
Cory LaViska
c271b07476 fix build 2022-02-11 08:25:11 -05:00
Cory LaViska
6b428c1ea9 revert param 2022-02-11 08:03:41 -05:00
Cory LaViska
5641ba4a14 update scripts 2022-02-11 08:00:09 -05:00
Cory LaViska
461c7099ed fix tsc param 2022-02-11 07:58:54 -05:00
Cory LaViska
81871868c4 2.0.0-beta.66 2022-02-10 17:48:58 -05:00
Cory LaViska
191a835d9f update changelog 2022-02-10 17:43:18 -05:00
Cory LaViska
0d7aabe920 fix indentation 2022-02-10 17:42:41 -05:00
Cory LaViska
1b8b7823c2 log tsc 2022-02-10 16:41:20 -05:00
Cory LaViska
75ca306959 2.0.0-beta.65 2022-02-10 10:35:15 -05:00
Cory LaViska
37994de120 update changelog 2022-02-10 10:34:45 -05:00
Cory LaViska
3e35b0f7c6 add source to dialog/drawer event 2022-02-10 10:34:22 -05:00
Cory LaViska
f555a3323e update bootstrap-icons 2022-02-10 09:02:48 -05:00
Cory LaViska
a57526a0ff fixes #666 2022-02-10 08:56:41 -05:00
Cory LaViska
68001b00f3 update changelog 2022-02-07 08:52:32 -05:00
Buni48
7fbc248aa7 added spacing css custom property to docs (#664) 2022-02-07 08:50:46 -05:00
Cory LaViska
ec63d4c528 improve search results 2022-02-04 09:37:57 -05:00
Cory LaViska
c368af633c use event.reactName 2022-02-04 09:28:35 -05:00
Cory LaViska
486fe1dfc4 ignore empty values 2022-02-03 17:12:25 -05:00
Cory LaViska
271ae9a36a add display-label part 2022-02-03 08:31:52 -05:00
Cory LaViska
18513724a0 update cloud dev options 2022-02-01 17:04:07 -05:00
Ofer Shaal
9cfb652b29 Adding Gitpod support (#661)
* Adding Gitpod setup

* remove specifying vscode extensions in gitpod

* Allow ports 4000-4999

* Make local dev env instructions the first option
2022-02-01 16:53:49 -05:00
Cory LaViska
fbec7bd360 fix disabled screen reader bug; closes #658 2022-02-01 09:19:25 -05:00
Cory LaViska
401aba407c update icons + deps 2022-02-01 09:16:38 -05:00
Cory LaViska
c9f14d7f58 exclude styles from manifest 2022-01-31 14:41:18 -05:00
Cory LaViska
aa7e32f81d fix link 2022-01-31 10:55:19 -05:00
Cory LaViska
6ab6ac81aa stop breaking when cspell is updated through the "quick fix" UI 2022-01-31 10:50:25 -05:00
Cory LaViska
f13672776a don't break build on spelling errors 2022-01-31 10:46:29 -05:00
Cory LaViska
13b299a3aa add word 2022-01-31 10:46:22 -05:00
Cory LaViska
7a764f51ec feather => lucide 2022-01-31 10:42:11 -05:00
Cory LaViska
71a93409fe prettier 2022-01-27 09:00:06 -05:00
Cory LaViska
f70961e67d refactor format-bytes to use Intl 2022-01-27 08:56:51 -05:00
Cory LaViska
8194d627ee Update deps 2022-01-26 09:36:07 -05:00
Cory LaViska
4e9573334a fix outdir bug 2022-01-26 08:46:20 -05:00
Cory LaViska
74cc1296c8 add word 2022-01-25 17:32:38 -05:00
Cory LaViska
4adcb8c938 fixes #571 2022-01-25 17:09:53 -05:00
Cory LaViska
4fdc5aa55f improve dialog/drawer a11y 2022-01-24 17:27:24 -05:00
Cory LaViska
fd43cb4fd7 fixes #656 2022-01-24 08:32:05 -05:00
Cory LaViska
e08236eaff restore spinner animation 2022-01-20 08:53:34 -05:00
Cory LaViska
27b5e3daa7 fix typo 2022-01-19 10:10:30 -05:00
Cory LaViska
955d3f9dd5 fix broken tabs 2022-01-19 10:01:22 -05:00
Cory LaViska
557d973ba4 revert rules 2022-01-19 09:37:07 -05:00
Cory LaViska
b9bf8887dc Merge branch 'CreativeTechGuy-bs-auto-sync' into next 2022-01-19 08:40:01 -05:00
Cory LaViska
5995258c5e Add whitespace 2022-01-19 08:39:48 -05:00
Jason O'Neill
2f46b6f507 dev: start BrowserSync timeout after server init 2022-01-18 15:11:00 -08:00
Jason O'Neill
dbb4be7cfa dev: reuse existing browser tab for dev server 2022-01-18 15:11:00 -08:00
Cory LaViska
a6a8da5aa4 update min node version 2022-01-18 09:23:48 -05:00
Cory LaViska
86706f31c6 Merge branch 'CreativeTechGuy-eslint-ts-a11y' into next 2022-01-18 09:22:28 -05:00
Cory LaViska
59ba63f875 Merge branch 'eslint-ts-a11y' of https://github.com/CreativeTechGuy/shoelace into CreativeTechGuy-eslint-ts-a11y 2022-01-18 08:58:14 -05:00
Cory LaViska
52933a528b Add note about setting multiselect values 2022-01-18 08:50:14 -05:00
Jason O'Neill
0330498bbb eslint: enable one-liner functions, dangling promises 2022-01-16 20:44:10 -08:00
Jason O'Neill
837dac17ea restore fsevents to package-lock.json 2022-01-15 23:19:04 -08:00
Jason O'Neill
9fb3b5cfed feat: add ESLint, improve types, improve a11y 2022-01-15 21:47:14 -08:00
Cory LaViska
2ad00deb38 2.0.0-beta.64 2022-01-11 09:47:00 -05:00
Cory LaViska
8fb8a5002d update 2022-01-11 09:46:23 -05:00
Cory LaViska
af9ee948ef update 2022-01-11 09:41:36 -05:00
Konnor Rogers
9eb76fe470 Fix: filled inputs looked bizarre with autofill. (#644)
* Update input.styles.ts

* Update input.styles.ts
2022-01-11 09:35:28 -05:00
Cory LaViska
6d766a8ce9 remove dead link 2022-01-11 09:30:15 -05:00
Cory LaViska
33afecf7da support for <form> elements; remove <sl-form> 2022-01-11 09:18:20 -05:00
Cory LaViska
938c7d2437 update lit 2022-01-06 09:11:28 -05:00
Cory LaViska
c3bee5e725 simplify HasSlotController args 2022-01-06 09:04:02 -05:00
Cory LaViska
bb46282b91 add min node version 2022-01-06 08:50:45 -05:00
Jason O'Neill
ca346ccbb2 update dependencies, cleanup, refine (#642)
* update dependencies, cleanup, refine

fixes #637

* update CI command to verify
2022-01-06 08:44:13 -05:00
Cory LaViska
46f05224ab use reactive controller for slot detection 2022-01-05 18:31:41 -05:00
Cory LaViska
1e3bac6031 trim whitespace 2022-01-05 18:26:39 -05:00
Cory LaViska
3f90a3f49d fix search suffix position in docs 2022-01-05 11:06:13 -05:00
Cory LaViska
099dea886f add start, end, panel parts to split panel 2022-01-05 11:02:39 -05:00
Cory LaViska
d4d253284d add start, end, panel parts to split panel 2022-01-05 11:02:14 -05:00
Jason O'Neill
d6e15f985c add cspell and fix typos
fixes 636
2021-12-31 17:39:16 -08:00
Cory LaViska
c1b0497624 add valueAsDate & valueAsNumber to input; fixes #570 2021-12-31 12:30:54 -05:00
Cory LaViska
f25e4827a2 remove the offending test 2021-12-31 11:25:49 -05:00
Cory LaViska
5d57a51618 fix test 2021-12-31 11:20:40 -05:00
Cory LaViska
d803ffcf95 update alt attrib 2021-12-31 11:18:44 -05:00
Cory LaViska
4de5f180b6 fix test 2021-12-31 11:05:55 -05:00
Cory LaViska
2bad321397 change alt to label 2021-12-31 11:02:27 -05:00
Cory LaViska
ab37cc9661 center icons 2021-12-31 10:53:38 -05:00
Cory LaViska
a9a5166da7 improve focus when clicking edge 2021-12-31 10:53:06 -05:00
Cory LaViska
5723ea3f8b api improvements 2021-12-30 18:14:07 -05:00
Cory LaViska
2daea0836a update tooltip 2021-12-30 18:12:29 -05:00
Cory LaViska
e05c66a973 show defaults 2021-12-30 18:11:07 -05:00
Cory LaViska
0295d9c573 fixes #596; improves radio a11y 2021-12-30 16:32:57 -05:00
Cory LaViska
d60e9f3bc2 remove unused var 2021-12-30 16:16:19 -05:00
Cory LaViska
d71d35b258 move init logic to connectedCallback 2021-12-30 13:09:50 -05:00
Cory LaViska
9988d76c3f fix ids 2021-12-30 12:14:39 -05:00
Cory LaViska
f55d0a67d9 update usage 2021-12-30 11:12:00 -05:00
Cory LaViska
171adf7310 add loading section 2021-12-29 11:16:33 -05:00
Cory LaViska
03a9890781 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2021-12-29 09:31:25 -05:00
Cory LaViska
bf2d7b9d92 fix typo 2021-12-28 10:24:26 -05:00
Cory LaViska
05da17e9cb Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2021-12-28 09:20:20 -05:00
David Gonzalez
f653f643f7 refactor(image-comparer): remove unused Y position (#635) 2021-12-28 09:20:13 -05:00
Cory LaViska
d742ea6efc remove relative positioning 2021-12-27 14:05:25 -05:00
Cory LaViska
1fb1103e2d fix examples 2021-12-27 14:04:31 -05:00
Cory LaViska
baea8b62be add react examples 2021-12-27 14:04:20 -05:00
Cory LaViska
fe3dd76f68 fix typo 2021-12-27 12:55:31 -05:00
Cory LaViska
6af6e9c2c0 fix test 2021-12-27 12:45:24 -05:00
Cory LaViska
707bfb9c78 fixes #633 2021-12-27 12:40:30 -05:00
Cory LaViska
316087d18c remove unnecessary calc() 2021-12-27 11:37:40 -05:00
Cory LaViska
46c538dffb revert logic 2021-12-27 10:31:57 -05:00
David Gonzalez
218f6cb8d1 fix(split-panel): add missing keys (#629)
* fix(split-panel): add missing keys

* feat(split-panel): improve handleKeyDown algorithm
2021-12-27 10:22:59 -05:00
Cory LaViska
05f6c7656c 2.0.0-beta.63 2021-12-23 12:02:03 -05:00
Cory LaViska
3534ae910e update version 2021-12-23 12:01:36 -05:00
Cory LaViska
dd65778017 fixes #626 2021-12-23 11:53:37 -05:00
Cory LaViska
67f3a4b164 reorder 2021-12-23 11:52:30 -05:00
Cory LaViska
fcf1fd9bec update docs 2021-12-23 11:39:25 -05:00
Cory LaViska
2ceccd201a almost 2021-12-23 11:23:14 -05:00
Cory LaViska
45edfeee2d update docs 2021-12-23 10:27:05 -05:00
Cory LaViska
2a6cf2aea2 refactor keyboard logic 2021-12-23 10:21:10 -05:00
Cory LaViska
8bb3e5d9c9 boom 2021-12-23 10:07:37 -05:00
Cory LaViska
d3ad2ec4f8 primary 2021-12-23 08:24:44 -05:00
Cory LaViska
a3ef96a799 all except min/max 2021-12-22 19:07:16 -05:00
Cory LaViska
a5b7f8fd6b rework 2021-12-22 18:32:27 -05:00
Cory LaViska
33accf65ef prefix light dom ids 2021-12-17 10:31:14 -05:00
Cory LaViska
e2012433cb add blur() 2021-12-17 09:27:23 -05:00
ErikOnBike
d6d05121e4 Add focus method to SlSelect (#625) 2021-12-17 09:15:47 -05:00
Cory LaViska
125392ce57 simplify spinner animation 2021-12-14 13:34:06 -05:00
Cory LaViska
fb20155485 type => variant 2021-12-13 17:38:40 -05:00
Cory LaViska
1d44ee2f45 simplify divider API 2021-12-13 17:16:50 -05:00
Cory LaViska
2a6e91477a refactor button using static expressions 2021-12-13 16:56:03 -05:00
Cory LaViska
302f3b57c5 fix tooltip formatter in react@ext 2021-12-09 09:39:24 -05:00
Cory LaViska
7d818c0590 update icon count 2021-12-07 17:04:27 -05:00
Cory LaViska
ab77fca2f5 2.0.0-beta.62 2021-12-07 17:02:33 -05:00
Cory LaViska
4d33e1388b update version 2021-12-07 17:02:08 -05:00
Cory LaViska
9bac03d2f3 update deps 2021-12-07 16:59:16 -05:00
Cory LaViska
68bb155793 fixes #602 2021-12-07 16:52:17 -05:00
Cory LaViska
2be6ec1711 test all three at once 2021-12-07 16:46:05 -05:00
Cory LaViska
27e254ac4d install playwright deps 2021-12-07 15:03:16 -05:00
Cory LaViska
a7a1fb45bb update localize 2021-12-07 14:27:45 -05:00
Cory LaViska
0732799ecb update localize 2021-12-07 14:11:00 -05:00
Cory LaViska
ea22ac6b37 update localize 2021-12-07 13:32:50 -05:00
Cory LaViska
aeacf40654 update changelog 2021-12-07 13:20:38 -05:00
Cory LaViska
f87cb8d940 use localize lib for utility components 2021-12-07 13:20:27 -05:00
Cory LaViska
f37907a55a add dutch to list 2021-12-07 13:18:37 -05:00
Cory LaViska
0538d5c0db update localize 2021-12-07 13:16:22 -05:00
Cory LaViska
9a84e126a1 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2021-12-07 12:28:56 -05:00
Jan van Hellemond
5ec633192f Added Dutch translation (#614) 2021-12-07 12:28:50 -05:00
Cory LaViska
7b87dc9d21 add he 2021-12-07 11:24:35 -05:00
Cory LaViska
35df355cc6 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2021-12-07 11:23:58 -05:00
Benny Powers
59830a4793 feat: hebrew translation (#613) 2021-12-07 11:13:20 -05:00
Cory LaViska
d685ce1e6e fix code 2021-12-07 10:51:27 -05:00
Cory LaViska
0eba0d4b4a add translations 2021-12-07 10:36:27 -05:00
Cory LaViska
b32d3e5c17 consistent name/code 2021-12-07 10:35:41 -05:00
Cory LaViska
d696f19764 fix quotes 2021-12-07 10:35:07 -05:00
Cory LaViska
1645c2103c Merge branch 'localize' of https://github.com/shoelace-style/shoelace into localize 2021-12-07 10:34:06 -05:00
Peter Siska
9dfac1dd6f Add FR translation (#612) 2021-12-07 10:34:01 -05:00
Peter Siska
2937dbfc3a Add de_CH translation (#611)
Region-specific translation for German (Switzerland). 

Initiated from here: https://github.com/shoelace-style/shoelace/pull/609#issuecomment-987711804
2021-12-07 10:32:56 -05:00
Cory LaViska
f3a1cf82ac add localization docs 2021-12-07 10:32:05 -05:00
Cory LaViska
84ae7d187b prettier 2021-12-07 10:07:02 -05:00
Cory LaViska
49ba670b36 no dash 2021-12-07 10:05:14 -05:00
Manuel Schmidt
78f9dcc68a Add german translation (#608)
* add german translation

* Update src/translations/de.ts

* Update src/translations/de.ts
2021-12-07 08:32:16 -05:00
Alan Dávalos
8258d84c23 Add Japanese translation (#606)
* add Japanese translation

* update label for Japanese
2021-12-07 08:20:23 -05:00
Max
a2a48415f7 Add portuguese translations (#605) 2021-12-07 08:19:11 -05:00
Denis Korablev
5539705bf3 add Russian translations (#607)
Co-authored-by: Denis Korablev <d.korablev@nominex.io>
2021-12-07 08:18:05 -05:00
Paweł Charasimiuk
1061873788 add Polish translation (#610) 2021-12-07 08:16:43 -05:00
Cory LaViska
a587c9523d run tests in chrome, firefox, and safari via playwright 2021-12-06 16:30:07 -05:00
Cory LaViska
eed18fba57 prettierrrr 2021-12-06 12:02:31 -05:00
Cory LaViska
df2158df0b update changelog 2021-12-06 12:02:04 -05:00
Cory LaViska
40ec49aeb9 improve term 2021-12-06 11:59:06 -05:00
Cory LaViska
4900bbf989 localize 2.0 2021-12-06 10:57:54 -05:00
Cory LaViska
3dc92ae8e8 fix switch tests 2021-12-03 15:04:26 -05:00
Cory LaViska
7255b0b30f locale => lang 2021-12-02 10:29:04 -05:00
Cory LaViska
b9b01d3816 "consistency is the key to success" 2021-12-01 17:40:58 -05:00
Cory LaViska
256103b02e whitespace + prettier 2021-11-29 09:55:31 -05:00
Mathias Picker
194c190519 Added check for PopperInstance before destroying it (#597) 2021-11-29 09:55:13 -05:00
Cory LaViska
8e5c258896 style fixes 2021-11-29 08:49:18 -05:00
Cory LaViska
fd375788f8 update color 2021-11-29 08:48:54 -05:00
Cory LaViska
d80fe902b3 fix lgtm warnings 2021-11-24 10:59:31 -05:00
Cory LaViska
4304d8badd fix tooltip positioning 2021-11-24 10:20:44 -05:00
Cory LaViska
ecdf507645 update wording 2021-11-24 10:12:42 -05:00
Cory LaViska
c4d271d767 fix base path examples 2021-11-24 10:03:38 -05:00
Cory LaViska
2dcd60efc4 fix focus 2021-11-24 09:54:58 -05:00
Cory LaViska
4251f2a7f7 fix search panel bg 2021-11-24 09:51:58 -05:00
Cory LaViska
4a58ad861c update wording 2021-11-24 09:04:49 -05:00
Cory LaViska
b87bbd569e less purple 2021-11-24 08:41:28 -05:00
Cory LaViska
11bad31b5f upgrade qr code to stable 2021-11-24 08:32:11 -05:00
Cory LaViska
d428ffe937 add color to images 2021-11-23 16:59:23 -05:00
Cory LaViska
4ff60abb93 fix wording 2021-11-23 16:58:24 -05:00
Cory LaViska
7a5a476ed1 fix input tokens 2021-11-23 16:58:11 -05:00
Cory LaViska
b47f3563de improve code contrast 2021-11-23 16:57:53 -05:00
Cory LaViska
a828addd28 fix instructions 2021-11-23 15:32:06 -05:00
Cory LaViska
93ce71acdd adjust color 2021-11-23 15:31:52 -05:00
Cory LaViska
a15ccfee1b Revert "Merge branch 'radio-group' of https://github.com/Trendy/shoelace into next"
This reverts commit e5cbee2770, reversing
changes made to 3897446cb7.
2021-11-23 11:05:04 -05:00
Cory LaViska
e5cbee2770 Merge branch 'radio-group' of https://github.com/Trendy/shoelace into next 2021-11-23 08:14:16 -05:00
Jeremiah Hoyet
e9f7c5ed5a Make the default the same as the getter default 2021-11-22 19:30:51 -05:00
Jeremiah Hoyet
3141590d28 Update react example 2021-11-22 19:27:12 -05:00
Jeremiah Hoyet
cfa800c1cd Fix getter 2021-11-22 19:18:07 -05:00
Jeremiah Hoyet
6eb79aacdb Review feedback updates 2021-11-22 18:58:43 -05:00
Jeremiah Hoyet
2ace7d4161 Update src/components/radio-group/radio-group.ts
Co-authored-by: Cory LaViska <cory@abeautifulsite.net>
2021-11-22 18:10:45 -05:00
Jeremiah Hoyet
b36d2edfde Clean up tests 2021-11-22 17:17:31 -05:00
Cory LaViska
3897446cb7 add visually hidden tests 2021-11-22 15:17:02 -05:00
Jeremiah Hoyet
d4c41a2b27 Move selection logic from radio to radio group 2021-11-22 14:46:10 -05:00
Jeremiah Hoyet
dfaabeead2 Clean up react example 2021-11-22 14:20:33 -05:00
Jeremiah Hoyet
989e368fb4 Remove required on sl-radio checks from sl-radio-group 2021-11-22 14:05:14 -05:00
Jeremiah Hoyet
0c6060eae7 Add required attribute to radio group and radio 2021-11-22 12:34:52 -05:00
Cory LaViska
8a766fe100 update changelog 2021-11-22 09:03:49 -05:00
Kazem Keshavarz
9afb32f526 Fix vscode custom data tag name (#593) 2021-11-22 08:40:23 -05:00
Cory LaViska
8ea8a20cc9 add dark mode to codepen 2021-11-22 08:32:53 -05:00
Cory LaViska
70f0c7d01e fix wording 2021-11-22 08:21:38 -05:00
Cory LaViska
f214f0f033 Merge branch 'next' of https://github.com/shoelace-style/shoelace into next 2021-11-19 16:18:13 -05:00
Cory LaViska
37425db04d improve search selection colors 2021-11-19 16:12:39 -05:00
Cory LaViska
357909401d update theme docs 2021-11-19 12:32:52 -05:00
Cory LaViska
87286593cb 2.0.0-beta.61 2021-11-19 10:49:59 -05:00
Cory LaViska
2e1a74f79a update version 2021-11-19 10:48:58 -05:00
Cory LaViska
341ea70dbc add accessibility commitment 2021-11-19 10:42:59 -05:00
Cory LaViska
54e4c57ae5 fixes #591 2021-11-19 08:36:59 -05:00
Cory LaViska
9432ffebad reduce base lightness slightly 2021-11-19 08:26:03 -05:00
Cory LaViska
c748792f16 improve text contrast in doc 2021-11-19 08:19:23 -05:00
Cory LaViska
f1b304304c improve string colors 2021-11-18 18:00:19 -05:00
Cory LaViska
8532f7df26 make it stable 2021-11-18 17:46:37 -05:00
Cory LaViska
9cb3314494 improve dark theme and remove rgb() from tokens 2021-11-18 17:41:03 -05:00
Cory LaViska
cfc7b2ac93 fix button slots 2021-11-18 08:01:00 -05:00
Cory LaViska
2f2709abc6 remove unused function 2021-11-18 08:00:28 -05:00
Cory LaViska
8fd8087370 fix docs 2021-11-17 09:26:22 -05:00
Cory LaViska
d140dc2c71 prettier 2021-11-17 09:22:41 -05:00
Cory LaViska
1a4f330bd5 update bs icons 2021-11-17 09:12:34 -05:00
ErikOnBike
65a0125035 Remove duplicate values for autocapitalize (#590) 2021-11-17 08:24:36 -05:00
Cory LaViska
bfe506dbf3 add expanded support 2021-11-16 10:49:26 -05:00
Cory LaViska
da7a177599 add react examples 2021-11-16 10:09:31 -05:00
Cory LaViska
fe677f133b add visually hidden component 2021-11-16 09:31:38 -05:00
Cory LaViska
d6e4d2f24b add border to control button 2021-11-16 09:30:23 -05:00
Cory LaViska
a14642b62a don't guess labels 2021-11-16 09:19:49 -05:00
Cory LaViska
9d223067ae add contribution links 2021-11-16 09:19:34 -05:00
Cory LaViska
39009a6ee6 add script tag import 2021-11-15 17:43:13 -05:00
Cory LaViska
0ea16b1d97 update docs 2021-11-15 17:42:53 -05:00
Cory LaViska
977e9e0019 update form examples 2021-11-15 09:36:30 -05:00
Cory LaViska
e186db3b8e npm audit 2021-11-12 17:50:48 -05:00
Cory LaViska
0135a37af8 a11y improvements; fixes #579 2021-11-12 17:40:26 -05:00
Cory LaViska
a923d1effc remove unused styles 2021-11-12 12:03:19 -05:00
Cory LaViska
11f7bf2bb1 fix example 2021-11-12 12:01:04 -05:00
Cory LaViska
b336cdffe5 add testing info 2021-11-12 11:20:04 -05:00
Cory LaViska
f85b9e1b2b update framework pages 2021-11-12 10:31:13 -05:00
Cory LaViska
1422e3ffb7 update intro 2021-11-12 10:09:04 -05:00
Cory LaViska
b1a080cb91 fix incorrect aria-controls 2021-11-12 09:59:29 -05:00
Cory LaViska
59ad01c560 fix lit dep 2021-11-12 09:55:53 -05:00
Cory LaViska
a24eaa6693 remove redundant role 2021-11-12 09:50:50 -05:00
Cory LaViska
b98b10c580 faster animations 2021-11-12 09:43:02 -05:00
Marcel Kuhmann
2fca01401b allow query strings (#582) 2021-11-11 10:55:26 -05:00
Thomas Klemm
f20296cf7c Docs: Fix typo in React setup code sample (#580) 2021-11-07 07:11:33 -05:00
Cory LaViska
fe041c5e10 fix typo 2021-11-06 08:28:47 -04:00
Cory LaViska
ca44d23031 2.0.0-beta.60 2021-11-05 11:57:49 -04:00
Cory LaViska
18452f692c update version 2021-11-05 11:57:33 -04:00
Cory LaViska
6aca68824a fixes #578 2021-11-05 11:53:53 -04:00
Cory LaViska
7177b9bf82 update intro 2021-11-05 11:51:24 -04:00
Cory LaViska
5b6e24bd13 fix example 2021-11-05 11:51:12 -04:00
Cory LaViska
cc93108df0 less verbose 2021-11-05 11:50:59 -04:00
Cory LaViska
95041b75b0 add react examples 2021-11-05 11:50:46 -04:00
Cory LaViska
0929799daf fix style attrs 2021-11-05 11:26:09 -04:00
Cory LaViska
c771534c43 fix className 2021-11-05 10:06:06 -04:00
Cory LaViska
3ffbc09630 improve flavor logic 2021-11-05 09:47:43 -04:00
Cory LaViska
de4207940c add react event names to manifest 2021-11-05 09:23:30 -04:00
Cory LaViska
3eb7d6337a fix mutation observer in react 2021-11-05 09:22:59 -04:00
Cory LaViska
1dd556d6c8 react examples and fixes 2021-11-04 18:12:47 -04:00
Cory LaViska
a250d9b184 support react imports in examples; set base path 2021-11-04 08:12:01 -04:00
Cory LaViska
bb6cedfce4 2.0.0-beta.59 2021-11-04 07:27:30 -04:00
Cory LaViska
a4c9b9c8cf add react support into lib 2021-11-04 07:27:18 -04:00
Cory LaViska
c88ea6666b update react imports 2021-11-02 17:13:12 -04:00
Cory LaViska
5ecd73c599 update example 2021-11-02 16:54:17 -04:00
Cory LaViska
84739ba695 update clear icon 2021-11-02 16:52:31 -04:00
Cory LaViska
3bb1e9ff91 update bootstrap icons 2021-11-02 16:46:17 -04:00
572 changed files with 74901 additions and 32998 deletions

View File

@@ -1,4 +1,4 @@
# http://editorconfig.org
# https://editorconfig.org
root = true

10
.eslintignore Normal file
View File

@@ -0,0 +1,10 @@
.cache
docs/dist
docs/search.json
docs/**/*.min.js
dist
examples
node_modules
src/react
scripts

211
.eslintrc.cjs Normal file
View File

@@ -0,0 +1,211 @@
/* eslint-env node */
module.exports = {
plugins: [
'@typescript-eslint',
'wc',
'lit',
'lit-a11y',
'chai-expect',
'chai-friendly',
'import',
'sort-imports-es6-autofix'
],
extends: [
'eslint:recommended',
'plugin:wc/recommended',
'plugin:wc/best-practice',
'plugin:lit/recommended',
'plugin:lit-a11y/recommended'
],
env: {
es2021: true,
browser: true
},
parserOptions: {
sourceType: 'module'
},
overrides: [
{
extends: [
'plugin:@typescript-eslint/eslint-recommended',
'plugin:@typescript-eslint/recommended',
'plugin:@typescript-eslint/recommended-requiring-type-checking'
],
parser: '@typescript-eslint/parser',
parserOptions: {
sourceType: 'module',
project: './tsconfig.json',
tsconfigRootDir: __dirname
},
files: ['*.ts'],
rules: {
'default-param-last': 'off',
'@typescript-eslint/default-param-last': 'error',
'no-empty-function': 'off',
'@typescript-eslint/no-empty-function': 'warn',
'no-implied-eval': 'off',
'@typescript-eslint/no-implied-eval': 'error',
'no-invalid-this': 'off',
'@typescript-eslint/no-invalid-this': 'error',
'no-shadow': 'off',
'@typescript-eslint/no-shadow': 'error',
'no-throw-literal': 'off',
'@typescript-eslint/no-throw-literal': 'error',
'no-unused-expressions': 'off',
'@typescript-eslint/prefer-regexp-exec': 'off',
'@typescript-eslint/no-unused-expressions': 'error',
'@typescript-eslint/unbound-method': 'off',
'@typescript-eslint/no-non-null-assertion': 'off',
'@typescript-eslint/no-floating-promises': 'off',
'@typescript-eslint/no-misused-promises': [
'error',
{
checksVoidReturn: false
}
],
'@typescript-eslint/consistent-type-assertions': [
'warn',
{
assertionStyle: 'as',
objectLiteralTypeAssertions: 'never'
}
],
'@typescript-eslint/consistent-type-imports': 'warn',
'@typescript-eslint/no-base-to-string': 'error',
'@typescript-eslint/no-confusing-non-null-assertion': 'error',
'@typescript-eslint/no-invalid-void-type': 'error',
'@typescript-eslint/no-require-imports': 'error',
'@typescript-eslint/no-unnecessary-boolean-literal-compare': 'warn',
'@typescript-eslint/no-unnecessary-condition': 'off',
'@typescript-eslint/no-unnecessary-qualifier': 'warn',
'@typescript-eslint/non-nullable-type-assertion-style': 'warn',
'@typescript-eslint/prefer-for-of': 'warn',
'@typescript-eslint/prefer-optional-chain': 'warn',
'@typescript-eslint/prefer-ts-expect-error': 'warn',
'@typescript-eslint/prefer-return-this-type': 'error',
'@typescript-eslint/prefer-string-starts-ends-with': 'warn',
'@typescript-eslint/require-array-sort-compare': 'error',
'@typescript-eslint/unified-signatures': 'warn',
'@typescript-eslint/array-type': 'warn',
'@typescript-eslint/consistent-type-definitions': ['warn', 'interface'],
'@typescript-eslint/member-delimiter-style': 'warn',
'@typescript-eslint/method-signature-style': 'warn',
'@typescript-eslint/no-extraneous-class': 'error',
'@typescript-eslint/no-redundant-type-constituents': 'off',
'@typescript-eslint/parameter-properties': 'error',
'@typescript-eslint/strict-boolean-expressions': 'off'
}
},
{
files: ['**/*.cjs'],
env: {
node: true
}
},
{
extends: ['plugin:chai-expect/recommended', 'plugin:chai-friendly/recommended'],
files: ['*.test.ts'],
rules: {
'@typescript-eslint/no-unsafe-call': 'off',
'@typescript-eslint/no-unused-expressions': 'off'
}
}
],
rules: {
'no-template-curly-in-string': 'error',
'array-callback-return': 'error',
'comma-dangle': 'off',
'consistent-return': 'error',
curly: 'off',
'default-param-last': 'error',
eqeqeq: 'error',
'lit-a11y/click-events-have-key-events': 'off',
'no-constructor-return': 'error',
'no-empty-function': 'warn',
'no-eval': 'error',
'no-extend-native': 'error',
'no-extra-bind': 'error',
'no-floating-decimal': 'error',
'no-implicit-coercion': 'off',
'no-implicit-globals': 'error',
'no-implied-eval': 'error',
'no-invalid-this': 'error',
'no-labels': 'error',
'no-lone-blocks': 'error',
'no-new': 'error',
'no-new-func': 'error',
'no-new-wrappers': 'error',
'no-octal-escape': 'error',
'no-proto': 'error',
'no-return-assign': 'warn',
'no-script-url': 'error',
'no-self-compare': 'warn',
'no-sequences': 'warn',
'no-throw-literal': 'error',
'no-unmodified-loop-condition': 'error',
'no-unused-expressions': 'warn',
'no-useless-call': 'error',
'no-useless-concat': 'error',
'no-useless-return': 'warn',
'prefer-promise-reject-errors': 'error',
radix: 'off',
'require-await': 'error',
'wrap-iife': ['warn', 'inside'],
'no-shadow': 'error',
'no-array-constructor': 'error',
'no-bitwise': 'error',
'no-multi-assign': 'warn',
'no-new-object': 'error',
'no-useless-computed-key': 'warn',
'no-useless-rename': 'warn',
'no-var': 'error',
'prefer-const': 'warn',
'prefer-numeric-literals': 'warn',
'prefer-object-spread': 'warn',
'prefer-rest-params': 'warn',
'prefer-spread': 'warn',
'prefer-template': 'off',
'no-else-return': 'off',
'func-names': ['warn', 'never'],
'one-var': ['warn', 'never'],
'operator-assignment': 'warn',
'prefer-arrow-callback': 'warn',
'no-restricted-imports': [
'warn',
{
paths: [
{
name: '.',
message: 'Usage of local index imports is not allowed.'
},
{
name: './index',
message: 'Import from the source file instead.'
}
]
}
],
'import/extensions': [
'error',
'always',
{
ignorePackages: true,
pattern: {
js: 'always',
ts: 'never'
}
}
],
'import/no-duplicates': 'warn',
'sort-imports-es6-autofix/sort-imports-es6': [
2,
{
ignoreCase: true,
ignoreMemberSort: false,
memberSyntaxSortOrder: ['none', 'all', 'multiple', 'single']
}
],
'wc/guard-super-call': 'off'
}
};

View File

@@ -3,8 +3,7 @@ name: Bug Report
about: Create a bug report to help us fix a demonstrable problem with code in the library.
title: ''
labels: bug
assignees: claviska
assignees:
---
### Describe the bug
@@ -29,8 +28,8 @@ If applicable, add screenshots to help explain the bug.
### Browser / OS
- OS: [e.g. Mac, Windows]
- Browser [e.g. Chrome, Firefox, Safari]
- Browser version [e.g. 22]
- Browser: [e.g. Chrome, Firefox, Safari]
- Browser version: [e.g. 22]
### Additional information
Provide any additional information about the bug here.

View File

@@ -3,8 +3,6 @@ name: Feature Request
about: Suggest an idea for this project.
title: ''
labels: feature
assignees: claviska
---
### What issue are you having?

2
.github/SECURITY.md vendored
View File

@@ -4,4 +4,4 @@ We take security issues in Shoelace very seriously and appreciate your efforts t
To report a security issue, email [cory@abeautifulsite.net](mailto:cory@abeautifulsite.net) and include "SHOELACE SECURITY" in the subject line.
Well respond as soon as possible and keep you updated throughout the process.
We'll respond as soon as possible and keep you updated throughout the process.

View File

@@ -5,27 +5,26 @@ name: Node.js CI
on:
push:
branches: [ next ]
branches: [next]
pull_request:
branches: [ next ]
branches: [next]
jobs:
build:
runs-on: ubuntu-latest
strategy:
matrix:
node-version: [14.x, 16.x]
node-version: [18.x]
# See supported Node.js release schedule at https://nodejs.org/en/about/releases/
steps:
- uses: actions/checkout@v2
- name: Use Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v2
with:
node-version: ${{ matrix.node-version }}
cache: 'npm'
- run: npm ci
- run: npm run build --if-present
- run: npm test
- uses: actions/checkout@v3
- name: Use Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v3
with:
node-version: ${{ matrix.node-version }}
cache: 'npm'
- run: npx playwright install-deps
- run: npm ci
- run: npm run verify

10
.gitignore vendored
View File

@@ -1,7 +1,9 @@
.DS_Store
_site
.cache
docs/dist
docs/search.json
.DS_Store
dist
examples
docs/assets/images/sprite.svg
node_modules
src/react
cdn
web-types.json

28
.gitpod.yml Normal file
View File

@@ -0,0 +1,28 @@
tasks:
- init: npm install && npm run build
command: npm run start
ports:
- port: 3001
onOpen: ignore
- port: 4000-4999
onOpen: open-preview
github:
prebuilds:
# enable for the master/default branch (defaults to true)
master: true
# enable for all branches in this repo (defaults to false)
branches: true
# enable for pull requests coming from this repo (defaults to true)
pullRequests: true
# enable for pull requests coming from forks (defaults to false)
pullRequestsFromForks: true
# add a check to pull requests (defaults to true)
addCheck: true
# add a "Review in Gitpod" button as a comment to pull requests (defaults to false)
addComment: false
# add a "Review in Gitpod" button to the pull request's description (defaults to false)
addBadge: true
# add a label once the prebuild is ready to pull requests (defaults to false)
addLabel: true

4
.husky/pre-commit Normal file
View File

@@ -0,0 +1,4 @@
#!/bin/sh
. "$(dirname "$0")/_/husky.sh"
npx --no-install lint-staged

View File

@@ -1,10 +1,14 @@
*.hbs
*.md
.cache
.github
cspell.json
dist
docs/*.md
docs/search.json
src/components/icon/icons
src/react/index.ts
node_modules
package.json
package-lock.json
tsconfig.json
cdn
_site

View File

@@ -1,8 +1,9 @@
{
"recommendations": [
"ms-vscode.vscode-typescript-tslint-plugin",
"dbaeumer.vscode-eslint",
"esbenp.prettier-vscode",
"bierner.lit-html",
"bashmish.es6-string-css"
"bashmish.es6-string-css",
"streetsidesoftware.code-spell-checker"
]
}

View File

@@ -1,4 +1,7 @@
{
"editor.formatOnSave": true,
"editor.defaultFormatter": "esbenp.prettier-vscode"
"editor.defaultFormatter": "esbenp.prettier-vscode",
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true
}
}

View File

@@ -23,7 +23,7 @@ Twitter: [@shoelace_style](https://twitter.com/shoelace_style)
## Shoemakers 🥾
Shoemakers, or "Shoelace developers," can use this documentation to learn how to build Shoelace from source. You will need Node >= 14 to build and run the project locally. It is preferred, but not required, to use npm 7.
Shoemakers, or "Shoelace developers," can use this documentation to learn how to build Shoelace from source. You will need Node >= 14.17 to build and run the project locally.
**You don't need to do any of this to use Shoelace!** This page is for people who want to contribute to the project, tinker with the source, or create a custom build of Shoelace.
@@ -51,9 +51,7 @@ Once you've cloned the repo, run the following command.
npm start
```
This will spin up the Shoelace dev server. After the initial build, a browser will open automatically. There is currently no hot module reloading (HMR), as browser's don't provide a way to reregister custom elements, but most changes to the source will reload the browser automatically.
The documentation is powered by Docsify, which uses raw markdown files to generate pages. As such, no static files are built for the docs.
This will spin up the dev server. After the initial build, a browser will open automatically. There is currently no hot module reloading (HMR), as browser's don't provide a way to reregister custom elements, but most changes to the source will reload the browser automatically.
### Building

184
cspell.json Normal file
View File

@@ -0,0 +1,184 @@
{
"version": "0.2",
"words": [
"activedescendant",
"allowfullscreen",
"animationend",
"Animista",
"apos",
"atrule",
"autocorrect",
"autofix",
"autoload",
"autoloader",
"autoloading",
"autoplay",
"bezier",
"boxicons",
"CACHEABLE",
"callout",
"callouts",
"cdndir",
"chatbubble",
"checkmark",
"claviska",
"Clippy",
"codebases",
"codepen",
"colocated",
"colour",
"combobox",
"Commonmark",
"Composability",
"Consolas",
"contenteditable",
"copydir",
"Cotte",
"coverpage",
"crossorigin",
"crutchcorn",
"csspart",
"cssproperty",
"datetime",
"describedby",
"Docsify",
"dogfood",
"dropdowns",
"easings",
"endraw",
"enterkeyhint",
"eqeqeq",
"erroneou",
"errormessage",
"esbuild",
"exportmaps",
"exportparts",
"fieldsets",
"formaction",
"formdata",
"formenctype",
"formmethod",
"formnovalidate",
"formtarget",
"FOUC",
"FOUCE",
"fullscreen",
"gestern",
"giga",
"globby",
"Grayscale",
"haspopup",
"heroicons",
"hexa",
"Iconoir",
"Iframes",
"iife",
"inputmode",
"ionicon",
"ionicons",
"jsDelivr",
"jsfiddle",
"jsonata",
"keydown",
"keyframes",
"Kool",
"labelledby",
"Laravel",
"LaViska",
"linkify",
"listbox",
"listitem",
"litelement",
"lowercasing",
"Lucide",
"maxlength",
"Menlo",
"menuitemcheckbox",
"menuitemradio",
"middlewares",
"minlength",
"monospace",
"mousedown",
"mousemove",
"mouseup",
"multiselectable",
"nextjs",
"nocheck",
"noopener",
"noreferrer",
"novalidate",
"npmdir",
"Numberish",
"outdir",
"ParamagicDev",
"peta",
"petabit",
"prismjs",
"progressbar",
"radiogroup",
"Railsbyte",
"remixicon",
"reregister",
"resizer",
"resizers",
"retargeted",
"RETRYABLE",
"rgba",
"roadmap",
"Roboto",
"roledescription",
"Sapan",
"saturationl",
"Schilp",
"scrollbars",
"scrollend",
"scroller",
"Segoe",
"semibold",
"sitedir",
"slotchange",
"smartquotes",
"spacebar",
"stylesheet",
"Tabbable",
"tabindex",
"tabler",
"tablist",
"tabpanel",
"templating",
"tera",
"testid",
"textareas",
"textfield",
"tinycolor",
"transitionend",
"treeitem",
"treeshaking",
"Triaging",
"turbolinks",
"typeof",
"unbundles",
"unbundling",
"unicons",
"unsanitized",
"unsupportive",
"valpha",
"valuenow",
"valuetext",
"WEBP",
"Webpacker",
"wordmark"
],
"ignorePaths": [
"package.json",
"package-lock.json",
"docs/assets/examples/include.html",
".vscode/**",
"src/translations/!(en).ts",
"**/*.min.js"
],
"ignoreRegExpList": [
"(^|[^a-z])sl[a-z]*(^|[^a-z])"
],
"useGitignore": true
}

View File

@@ -1,31 +1,80 @@
import * as path from 'path';
import { customElementJetBrainsPlugin } from 'custom-element-jet-brains-integration';
import { customElementVsCodePlugin } from 'custom-element-vs-code-integration';
import { parse } from 'comment-parser';
import { pascalCase } from 'pascal-case';
import commandLineArgs from 'command-line-args';
import fs from 'fs';
import commentParser from 'comment-parser';
const packageData = JSON.parse(fs.readFileSync('./package.json', 'utf8'));
const { name, description, version, author, homepage, license } = packageData;
const noDash = string => string.replace(/^\s?-/, '').trim();
const { outdir } = commandLineArgs([
{ name: 'litelement', type: String },
{ name: 'analyze', defaultOption: true },
{ name: 'outdir', type: String }
]);
function noDash(string) {
return string.replace(/^\s?-/, '').trim();
}
function replace(string, terms) {
terms.forEach(({ from, to }) => {
string = string?.replace(from, to);
});
return string;
}
export default {
globs: ['src/components/**/*.ts'],
exclude: ['**/*.test.ts'],
globs: ['src/components/**/*.component.ts'],
exclude: ['**/*.styles.ts', '**/*.test.ts'],
plugins: [
// Append package data
{
name: 'shoelace-package-data',
packageLinkPhase({ customElementsManifest, context }) {
packageLinkPhase({ customElementsManifest }) {
customElementsManifest.package = { name, description, version, author, homepage, license };
}
},
// Infer tag names because we no longer use @customElement decorators.
{
name: 'shoelace-infer-tag-names',
analyzePhase({ ts, node, moduleDoc }) {
switch (node.kind) {
case ts.SyntaxKind.ClassDeclaration: {
const className = node.name.getText();
const classDoc = moduleDoc?.declarations?.find(declaration => declaration.name === className);
const importPath = moduleDoc.path;
// This is kind of a best guess at components. "thing.component.ts"
if (!importPath.endsWith('.component.ts')) {
return;
}
const tagNameWithoutPrefix = path.basename(importPath, '.component.ts');
const tagName = 'sl-' + tagNameWithoutPrefix;
classDoc.tagNameWithoutPrefix = tagNameWithoutPrefix;
classDoc.tagName = tagName;
// This used to be set to true by @customElement
classDoc.customElement = true;
}
}
}
},
// Parse custom jsDoc tags
{
name: 'shoelace-custom-tags',
analyzePhase({ ts, node, moduleDoc, context }) {
analyzePhase({ ts, node, moduleDoc }) {
switch (node.kind) {
case ts.SyntaxKind.ClassDeclaration:
case ts.SyntaxKind.ClassDeclaration: {
const className = node.name.getText();
const classDoc = moduleDoc?.declarations?.find(declaration => declaration.name === className);
const customTags = ['animation', 'dependency', 'since', 'status'];
const customTags = ['animation', 'dependency', 'documentation', 'since', 'status', 'title'];
let customComments = '/**';
node.jsDoc?.forEach(jsDoc => {
@@ -38,8 +87,11 @@ export default {
});
});
const parsed = commentParser.parse(customComments + '\n */');
parsed[0].tags?.map(t => {
// This is what allows us to map JSDOC comments to ReactWrappers.
classDoc['jsDoc'] = node.jsDoc?.map(jsDoc => jsDoc.getFullText()).join('\n');
const parsed = parse(`${customComments}\n */`);
parsed[0].tags?.forEach(t => {
switch (t.tag) {
// Animations
case 'animation':
@@ -61,8 +113,10 @@ export default {
break;
// Value-only metadata tags
case 'documentation':
case 'since':
case 'status':
case 'title':
classDoc[t.tag] = t.name;
break;
@@ -79,8 +133,83 @@ export default {
});
}
});
}
}
}
}
},
{
name: 'shoelace-react-event-names',
analyzePhase({ ts, node, moduleDoc }) {
switch (node.kind) {
case ts.SyntaxKind.ClassDeclaration: {
const className = node.name.getText();
const classDoc = moduleDoc?.declarations?.find(declaration => declaration.name === className);
if (classDoc?.events) {
classDoc.events.forEach(event => {
event.reactName = `on${pascalCase(event.name)}`;
event.eventName = `${pascalCase(event.name)}Event`;
});
}
}
}
}
},
{
name: 'shoelace-translate-module-paths',
packageLinkPhase({ customElementsManifest }) {
customElementsManifest?.modules?.forEach(mod => {
//
// CEM paths look like this:
//
// src/components/button/button.ts
//
// But we want them to look like this:
//
// components/button/button.js
//
const terms = [
{ from: /^src\//, to: '' }, // Strip the src/ prefix
{ from: /\.component.(t|j)sx?$/, to: '.js' } // Convert .ts to .js
];
mod.path = replace(mod.path, terms);
for (const ex of mod.exports ?? []) {
ex.declaration.module = replace(ex.declaration.module, terms);
}
for (const dec of mod.declarations ?? []) {
if (dec.kind === 'class') {
for (const member of dec.members ?? []) {
if (member.inheritedFrom) {
member.inheritedFrom.module = replace(member.inheritedFrom.module, terms);
}
}
}
}
});
}
},
// Generate custom VS Code data
customElementVsCodePlugin({
outdir,
cssFileName: null,
referencesTemplate: (_, tag) => [
{
name: 'Documentation',
url: `https://shoelace.style/components/${tag.replace('sl-', '')}`
}
]
}),
customElementJetBrainsPlugin({
excludeCss: true,
referencesTemplate: (_, tag) => {
return {
name: 'Documentation',
url: `https://shoelace.style/components/${tag.replace('sl-', '')}`
};
}
})
]
};

View File

@@ -1,5 +0,0 @@
# Not Found
<img class="not-found-image" src="/assets/images/undraw-not-found.svg" alt="Cute monsters hiding behind a tree">
Sorry, I couldn't find that page. Have you tried pressing <kbd>/</kbd> to search?

View File

@@ -0,0 +1,349 @@
{% extends "default.njk" %}
{# Find the component based on the `tag` front matter #}
{% set component = getComponent('sl-' + page.fileSlug) %}
{% block content %}
{# Determine the badge variant #}
{% if component.status == 'stable' %}
{% set badgeVariant = 'primary' %}
{% elseif component.status == 'experimental' %}
{% set badgeVariant = 'warning' %}
{% elseif component.status == 'planned' %}
{% set badgeVariant = 'neutral' %}
{% elseif component.status == 'deprecated' %}
{% set badgeVariant = 'danger' %}
{% else %}
{% set badgeVariant = 'neutral' %}
{% endif %}
{# Header #}
<header class="component-header">
<h1>{{ component.name | classNameToComponentName }}</h1>
<div class="component-header__tag">
<code>&lt;{{ component.tagName }}&gt; | {{ component.name }}</code>
</div>
<div class="component-header__info">
<sl-badge variant="neutral" pill>
Since {{component.since or '?' }}
</sl-badge>
<sl-badge variant="{{ badgeVariant }}" pill style="text-transform: capitalize;">
{{ component.status }}
</sl-badge>
</div>
</header>
<p class="component-summary">
{% if component.summary %}
{{ component.summary | markdownInline | safe }}
{% endif %}
</p>
{# Markdown content #}
{{ content | safe }}
{# Importing #}
<h2>Importing</h2>
<p>
If you're using the autoloader or the traditional loader, you can ignore this section. Otherwise, feel free to use
any of the following snippets to <a href="/getting-started/installation#cherry-picking">cherry pick</a> this component.
</p>
<sl-tab-group>
<sl-tab slot="nav" panel="script">Script</sl-tab>
<sl-tab slot="nav" panel="import">Import</sl-tab>
<sl-tab slot="nav" panel="bundler">Bundler</sl-tab>
<sl-tab slot="nav" panel="react">React</sl-tab>
<sl-tab-panel name="script">
<p>
To import this component from <a href="https://www.jsdelivr.com/package/npm/@shoelace-style/shoelace">the CDN</a>
using a script tag:
</p>
<pre><code class="language-html">&lt;script type=&quot;module&quot; src=&quot;https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@{{ meta.version }}/{{ meta.cdndir }}/{{ component.path }}&quot;&gt;&lt;/script&gt;</code></pre>
</sl-tab-panel>
<sl-tab-panel name="import">
<p>
To import this component from <a href="https://www.jsdelivr.com/package/npm/@shoelace-style/shoelace">the CDN</a>
using a JavaScript import:
</p>
<pre><code class="language-js">import 'https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@{{ meta.version }}/{{ meta.cdndir }}/{{ component.path }}';</code></pre>
</sl-tab-panel>
<sl-tab-panel name="bundler">
<p>
To import this component using <a href="{{ rootUrl('/getting-started/installation#bundling') }}">a bundler</a>:
</p>
<pre><code class="language-js">import '@shoelace-style/shoelace/{{ meta.npmdir }}/{{ component.path }}';</code></pre>
</sl-tab-panel>
<sl-tab-panel name="react">
<p>
To import this component as a <a href="/frameworks/react">React component</a>:
</p>
<pre><code class="language-js">import {{ component.name }} from '@shoelace-style/shoelace/{{ meta.npmdir }}/react/{{ component.tagNameWithoutPrefix }}';</code></pre>
</sl-tab-panel>
</sl-tab-group>
{# Slots #}
{% if component.slots.length %}
<h2>Slots</h2>
<table>
<thead>
<tr>
<th class="table-name">Name</th>
<th class="table-description">Description</th>
</tr>
</thead>
<tbody>
{% for slot in component.slots %}
<tr>
<td class="nowrap">
{% if slot.name %}
<code>{{ slot.name }}</code>
{% else %}
(default)
{% endif %}
</td>
<td>{{ slot.description | markdownInline | safe }}</td>
</tr>
{% endfor %}
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/usage#slots') }}">using slots</a>.</em></p>
{% endif %}
{# Properties #}
{% if component.properties.length %}
<h2>Properties</h2>
<table>
<thead>
<tr>
<th class="table-name">Name</th>
<th class="table-description">Description</th>
<th class="table-reflects">Reflects</th>
<th class="table-type">Type</th>
<th class="table-default">Default</th>
</tr>
</thead>
<tbody>
{% for prop in component.properties %}
<tr>
<td>
<code class="nowrap">{{ prop.name }}</code>
{% if prop.attribute | length > 0 %}
{% if prop.attribute != prop.name %}
<br>
<sl-tooltip content="This attribute is different from its property">
<small>
<code class="nowrap">
{{ prop.attribute }}
</code>
</small>
</sl-tooltip>
{% endif %}
{% endif %}
</td>
<td>
{{ prop.description | markdownInline | safe }}
</td>
<td style="text-align: center;">
{% if prop.reflects %}
<sl-icon label="yes" name="check-lg"></sl-icon>
{% endif %}
</td>
<td>
{% if prop.type.text %}
<code>{{ prop.type.text | markdownInline | safe }}</code>
{% else %}
-
{% endif %}
</td>
<td>
{% if prop.default %}
<code>{{ prop.default | markdownInline | safe }}</code>
{% else %}
-
{% endif %}
</td>
</tr>
{% endfor %}
<tr>
<td class="nowrap"><code>updateComplete</code></td>
<td>
A read-only promise that resolves when the component has
<a href="/getting-started/usage?#component-rendering-and-updating">finished updating</a>.
</td>
<td></td>
<td></td>
<td></td>
</tr>
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/usage#attributes-and-properties') }}">attributes and properties</a>.</em></p>
{% endif %}
{# Events #}
{% if component.events.length %}
<h2>Events</h2>
<table>
<thead>
<tr>
<th class="table-name" data-flavor="html">Name</th>
<th class="table-name" data-flavor="react">React Event</th>
<th class="table-description">Description</th>
<th class="table-event-detail">Event Detail</th>
</tr>
</thead>
<tbody>
{% for event in component.events %}
<tr>
<td data-flavor="html"><code class="nowrap">{{ event.name }}</code></td>
<td data-flavor="react"><code class="nowrap">{{ event.reactName }}</code></td>
<td>{{ event.description | markdownInline | safe }}</td>
<td>
{% if event.type.text %}
<code>{{ event.type.text }}</code>
{% else %}
-
{% endif %}
</td>
</tr>
{% endfor %}
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/usage#events') }}">events</a>.</em></p>
{% endif %}
{# Methods #}
{% if component.methods.length %}
<h2>Methods</h2>
<table>
<thead>
<tr>
<th class="table-name">Name</th>
<th class="table-description">Description</th>
<th class="table-arguments">Arguments</th>
</tr>
</thead>
<tbody>
{% for method in component.methods %}
<tr>
<td class="nowrap"><code>{{ method.name }}()</code></td>
<td>{{ method.description | markdownInline | safe }}</td>
<td>
{% if method.parameters.length %}
<code>
{% for param in method.parameters %}
{{ param.name }}: {{ param.type.text }}{% if not loop.last %},{% endif %}
{% endfor %}
</code>
{% else %}
-
{% endif %}
</td>
</tr>
{% endfor %}
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/usage#methods') }}">methods</a>.</em></p>
{% endif %}
{# Custom Properties #}
{% if component.cssProperties.length %}
<h2>Custom Properties</h2>
<table>
<thead>
<tr>
<th class="table-name">Name</th>
<th class="table-description">Description</th>
<th class="table-default">Default</th>
</tr>
</thead>
<tbody>
{% for cssProperty in component.cssProperties %}
<tr>
<td class="nowrap"><code>{{ cssProperty.name }}</code></td>
<td>{{ cssProperty.description | markdownInline | safe }}</td>
<td>{{ cssProperty.default }}</td>
</tr>
{% endfor %}
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/usage#custom-properties') }}">customizing CSS custom properties</a>.</em></p>
{% endif %}
{# CSS Parts #}
{% if component.cssParts.length %}
<h2>Parts</h2>
<table>
<thead>
<tr>
<th class="table-name">Name</th>
<th class="table-description">Description</th>
</tr>
</thead>
<tbody>
{% for cssPart in component.cssParts %}
<tr>
<td class="nowrap"><code>{{ cssPart.name }}</code></td>
<td>{{ cssPart.description | markdownInline | safe }}</td>
</tr>
{% endfor %}
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/customizing/#css-parts') }}">customizing CSS parts</a>.</em></p>
{% endif %}
{# Animations #}
{% if component.animations.length %}
<h2>Animations</h2>
<table>
<thead>
<tr>
<th class="table-name">Name</th>
<th class="table-description">Description</th>
</tr>
</thead>
<tbody>
{% for animation in component.animations %}
<tr>
<td class="nowrap"><code>{{ animation.name }}</code></td>
<td>{{ animation.description | markdownInline | safe }}</td>
</tr>
{% endfor %}
</tbody>
</table>
<p><em>Learn more about <a href="{{ rootUrl('/getting-started/customizing#animations') }}">customizing animations</a>.</em></p>
{% endif %}
{# Dependencies #}
{% if component.dependencies.length %}
<h2>Dependencies</h2>
<p>This component automatically imports the following dependencies.</p>
<ul>
{% for dependency in component.dependencies %}
<li><code>&lt;{{ dependency }}&gt;</code></li>
{% endfor %}
</ul>
{% endif %}
{% endblock %}

150
docs/_includes/default.njk Normal file
View File

@@ -0,0 +1,150 @@
<!DOCTYPE html>
<html
lang="en"
data-layout="{{ layout }}"
data-shoelace-version="{{ meta.version }}"
>
<head>
{# Metadata #}
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="description" content="{{ meta.description }}" />
<title>{{ meta.title }}</title>
{# Opt out of Turbo caching #}
<meta name="turbo-cache-control">
{# Stylesheets #}
<link rel="stylesheet" href="{{ assetUrl('styles/docs.css') }}" />
<link rel="stylesheet" href="{{ assetUrl('styles/code-previews.css') }}" />
<link rel="stylesheet" href="{{ assetUrl('styles/search.css') }}" />
{# Favicons #}
<link rel="icon" href="{{ assetUrl('images/logo.svg') }}" type="image/x-icon" />
{# Twitter Cards #}
<meta name="twitter:card" content="summary" />
<meta name="twitter:creator" content="shoelace_style" />
<meta name="twitter:image" content="{{ assetUrl(meta.image, true) }}" />
{# OpenGraph #}
<meta property="og:url" content="{{ rootUrl(page.url, true) }}" />
<meta property="og:title" content="{{ meta.title }}" />
<meta property="og:description" content="{{ meta.description }}" />
<meta property="og:image" content="{{ assetUrl(meta.image, true) }}" />
{# Shoelace #}
<link rel="stylesheet" href="/dist/themes/light.css" />
<link rel="stylesheet" href="/dist/themes/dark.css" />
<script type="module" src="/dist/shoelace-autoloader.js"></script>
{# Set the initial theme and menu states here to prevent flashing #}
<script>
(() => {
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
const theme = localStorage.getItem('theme') || 'auto';
document.documentElement.classList.toggle('sl-theme-dark', theme === 'dark' || (theme === 'auto' && prefersDark));
})();
</script>
{# Turbo + Scroll positioning #}
<script src="{{ assetUrl('scripts/turbo.js') }}" type="module"></script>
<script src="{{ assetUrl('scripts/docs.js') }}" defer></script>
<script src="{{ assetUrl('scripts/code-previews.js') }}" defer></script>
<script src="{{ assetUrl('scripts/lunr.js') }}" defer></script>
<script src="{{ assetUrl('scripts/search.js') }}" defer></script>
</head>
<body>
<a id="skip-to-main" class="visually-hidden" href="#main-content" data-smooth-link="false">
Skip to main content
</a>
{# Menu toggle #}
<button id="menu-toggle" type="button" aria-label="Menu">
<svg width="148" height="148" viewBox="0 0 148 148" xmlns="http://www.w3.org/2000/svg">
<g stroke="currentColor" stroke-width="18" fill="none" fill-rule="evenodd" stroke-linecap="round">
<path d="M9.5 125.5h129M9.5 74.5h129M9.5 23.5h129"></path>
</g>
</svg>
</button>
{# Icon toolbar #}
<div id="icon-toolbar">
{# GitHub #}
<a href="https://github.com/shoelace-style/shoelace" title="View Shoelace on GitHub">
<sl-icon name="github"></sl-icon>
</a>
{# Twitter #}
<a href="https://twitter.com/shoelace_style" title="Follow Shoelace on Twitter">
<sl-icon name="twitter"></sl-icon>
</a>
{# Theme selector #}
<sl-dropdown id="theme-selector" placement="bottom-end" distance="3">
<sl-button slot="trigger" size="small" variant="text" caret title="Press \ to toggle">
<sl-icon class="only-light" name="sun-fill"></sl-icon>
<sl-icon class="only-dark" name="moon-fill"></sl-icon>
</sl-button>
<sl-menu>
<sl-menu-item type="checkbox" value="light">Light</sl-menu-item>
<sl-menu-item type="checkbox" value="dark">Dark</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item type="checkbox" value="auto">System</sl-menu-item>
</sl-menu>
</sl-dropdown>
</div>
<aside id="sidebar" data-preserve-scroll>
<header>
<a href="/">
<img src="{{ assetUrl('images/wordmark.svg') }}" alt="Shoelace" />
</a>
<div class="sidebar-version">
{{ meta.version }}
</div>
</header>
<div class="sidebar-buttons">
<sl-button size="small" class="repo-button repo-button--github" href="https://github.com/shoelace-style/shoelace" target="_blank">
<sl-icon slot="prefix" name="github"></sl-icon> Code
</sl-button>
<sl-button size="small" class="repo-button repo-button--star" href="https://github.com/shoelace-style/shoelace/stargazers" target="_blank">
<sl-icon slot="prefix" name="star-fill"></sl-icon> Star
</sl-button>
<sl-button size="small" class="repo-button repo-button--twitter" href="https://twitter.com/shoelace_style" target="_blank">
<sl-icon slot="prefix" name="twitter"></sl-icon> Follow
</sl-button>
</div>
<button class="search-box" type="button" title="Press / to search" aria-label="Search" data-plugin="search">
<sl-icon name="search"></sl-icon>
<span>Search</span>
</button>
<nav>
{% include 'sidebar.njk' %}
</nav>
</aside>
{# Content #}
<main>
<a id="main-content"></a>
<article id="content" class="content{% if toc %} content--with-toc{% endif %}">
{% if toc %}
<div class="content__toc">
<ul>
<li class="top"><a href="#">{{ meta.title }}</a></li>
</ul>
</div>
{% endif %}
<div class="content__body">
{% block content %}
{{ content | safe }}
{% endblock %}
</div>
</article>
</main>
</body>
</html>

View File

@@ -0,0 +1,65 @@
<ul>
<li>
<h2>Getting Started</h2>
<ul>
<li><a href="/">Home</a></li>
<li><a href="/getting-started/installation">Installation</a></li>
<li><a href="/getting-started/usage">Usage</a></li>
<li><a href="/getting-started/themes">Themes</a></li>
<li><a href="/getting-started/customizing">Customizing</a></li>
<li><a href="/getting-started/form-controls">Form Controls</a></li>
<li><a href="/getting-started/localization">Localization</a></li>
</ul>
</li>
<li>
<h2>Frameworks</h2>
<ul>
<li><a href="/frameworks/react">React</a></li>
<li><a href="/frameworks/vue">Vue</a></li>
<li><a href="/frameworks/angular">Angular</a></li>
</ul>
</li>
<li>
<h2>Resources</h2>
<ul>
<li><a href="/resources/community">Community</a></li>
<li><a href="https://github.com/shoelace-style/shoelace/discussions">Help &amp; Support</a></li>
<li><a href="/resources/accessibility">Accessibility</a></li>
<li><a href="/resources/contributing">Contributing</a></li>
<li><a href="/resources/changelog">Changelog</a></li>
</ul>
</li>
<li>
<h2>Components</h2>
<ul>
{% for component in meta.components %}
<li>
<a href="/components/{{ component.tagName | removeSlPrefix }}">
{{ component.name | classNameToComponentName }}
</a>
</li>
{% endfor %}
</ul>
</li>
<li>
<h2>Design Tokens</h2>
<ul>
<li><a href="/tokens/typography">Typography</a></li>
<li><a href="/tokens/color">Color</a></li>
<li><a href="/tokens/spacing">Spacing</a></li>
<li><a href="/tokens/elevation">Elevation</a></li>
<li><a href="/tokens/border-radius">Border Radius</a></li>
<li><a href="/tokens/transition">Transition</a></li>
<li><a href="/tokens/z-index">Z-index</a></li>
<li><a href="/tokens/more">More Tokens</a></li>
</ul>
</li>
<li>
<h2>Tutorials</h2>
<ul>
<li><a href="/tutorials/integrating-with-laravel">Integrating with Laravel</a></li>
<li><a href="/tutorials/integrating-with-nextjs">Integrating with NextJS</a></li>
<li><a href="/tutorials/integrating-with-rails">Integrating with Rails</a></li>
</ul>
</li>
</ul>

View File

@@ -1,81 +0,0 @@
- Getting Started
- [Overview](/)
- [Installation](/getting-started/installation)
- [Usage](/getting-started/usage)
- [Themes](/getting-started/themes)
- [Customizing](/getting-started/customizing)
- Resources
- [Community](/resources/community)
- [Contributing](/resources/contributing)
- [Changelog](/resources/changelog)
- Components
- [Alert](/components/alert)
- [Avatar](/components/avatar)
- [Badge](/components/badge)
- [Breadcrumb](/components/breadcrumb)
- [Breadcrumb Item](/components/breadcrumb-item)
- [Button](/components/button)
- [Button Group](/components/button-group)
- [Card](/components/card)
- [Checkbox](/components/checkbox)
- [Color Picker](/components/color-picker)
- [Context Menu](/components/context-menu)
- [Details](/components/details)
- [Dialog](/components/dialog)
- [Divider](/components/divider)
- [Drawer](/components/drawer)
- [Dropdown](/components/dropdown)
- [Form](/components/form)
- [Icon](/components/icon)
- [Icon Button](/components/icon-button)
- [Image Comparer](/components/image-comparer)
- [Input](/components/input)
- [Menu](/components/menu)
- [Menu Item](/components/menu-item)
- [Menu Label](/components/menu-label)
- [Progress Bar](/components/progress-bar)
- [Progress Ring](/components/progress-ring)
- [QR Code](/components/qr-code)
- [Radio](/components/radio)
- [Radio Group](/components/radio-group)
- [Range](/components/range)
- [Rating](/components/rating)
- [Select](/components/select)
- [Skeleton](/components/skeleton)
- [Spinner](/components/spinner)
- [Switch](/components/switch)
- [Tab Group](/components/tab-group)
- [Tab](/components/tab)
- [Tab Panel](/components/tab-panel)
- [Tag](/components/tag)
- [Textarea](/components/textarea)
- [Tooltip](/components/tooltip)
<!--plop:component-->
- Utilities
- [Animated Image](/components/animated-image)
- [Animation](/components/animation)
- [Format Bytes](/components/format-bytes)
- [Format Date](/components/format-date)
- [Format Number](/components/format-number)
- [Include](/components/include)
- [Mutation Observer](/components/mutation-observer)
- [Relative Time](/components/relative-time)
- [Resize Observer](/components/resize-observer)
- [Responsive Media](/components/responsive-media)
- Design Tokens
- [Typography](/tokens/typography)
- [Color](/tokens/color)
- [Spacing](/tokens/spacing)
- [Elevation](/tokens/elevation)
- [Border Radius](/tokens/border-radius)
- [Transition](/tokens/transition)
- [Z-index](/tokens/z-index)
- Tutorials
- [Integrating with Laravel](/tutorials/integrating-with-laravel)
- [Integrating with NextJS](/tutorials/integrating-with-nextjs)
- [Integrating with Rails](/tutorials/integrating-with-rails)

View File

@@ -0,0 +1,35 @@
function normalizePathname(pathname) {
// Remove /index.html
if (pathname.endsWith('/index.html')) {
pathname = pathname.replace(/\/index\.html/, '');
}
// Remove trailing slashes
return pathname.replace(/\/$/, '');
}
/**
* Adds a class name to links that are currently active.
*/
module.exports = function (doc, options) {
options = {
className: 'active-link', // the class to add to active links
pathname: undefined, // the current pathname to compare
within: 'body', // element containing the target links
...options
};
const within = doc.querySelector(options.within);
if (!within) {
return doc;
}
within.querySelectorAll('a').forEach(link => {
if (normalizePathname(options.pathname) === normalizePathname(link.pathname)) {
link.classList.add(options.className);
}
});
return doc;
};

View File

@@ -0,0 +1,64 @@
const { createSlug } = require('./strings.cjs');
/**
* Turns headings into clickable, deep linkable anchors. The provided doc should be a document object provided by JSDOM.
* The same document will be returned with the appropriate DOM manipulations.
*/
module.exports = function (doc, options) {
options = {
levels: ['h1', 'h2', 'h3', 'h4', 'h5', 'h6'], // the headings to convert
className: 'anchor-heading', // the class name to add
within: 'body', // the element containing the target headings
...options
};
const within = doc.querySelector(options.within);
if (!within) {
return doc;
}
within.querySelectorAll('h1, h2, h3, h4, h5, h6').forEach(heading => {
const hasAnchor = heading.querySelector('a');
const anchor = doc.createElement('a');
let id = heading.textContent ?? '';
let suffix = 0;
// Skip heading levels we don't care about
if (!options.levels?.includes(heading.tagName.toLowerCase())) {
return;
}
// Convert dots to underscores
id = id.replace(/\./g, '_');
// Turn it into a slug
id = createSlug(id);
// Make sure it starts with a letter
if (!/^[a-z]/i.test(id)) {
id = `id_${id}`;
}
// Make sure the id is unique
const originalId = id;
while (doc.getElementById(id) !== null) {
id = `${originalId}-${++suffix}`;
}
if (hasAnchor || !id) return;
heading.setAttribute('id', id);
anchor.setAttribute('href', `#${encodeURIComponent(id)}`);
anchor.setAttribute('aria-label', `Direct link to "${heading.textContent}"`);
if (options.className) {
heading.classList.add(options.className);
}
// Append the anchor
heading.append(anchor);
});
return doc;
};

71
docs/_utilities/cem.cjs Normal file
View File

@@ -0,0 +1,71 @@
const customElementsManifest = require('../../dist/custom-elements.json');
//
// Export it here so we can import it elsewhere and use the same version
//
module.exports.customElementsManifest = customElementsManifest;
//
// Gets all components from custom-elements.json and returns them in a more documentation-friendly format.
//
module.exports.getAllComponents = function () {
const allComponents = [];
customElementsManifest.modules?.forEach(module => {
module.declarations?.forEach(declaration => {
if (declaration.customElement) {
// Generate the dist path based on the src path and attach it to the component
declaration.path = module.path.replace(/^src\//, 'dist/').replace(/\.ts$/, '.js');
// Remove members that are private or don't have a description
const members = declaration.members?.filter(member => member.description && member.privacy !== 'private');
const methods = members?.filter(prop => prop.kind === 'method' && prop.privacy !== 'private');
const properties = members?.filter(prop => {
// Look for a corresponding attribute
const attribute = declaration.attributes?.find(attr => attr.fieldName === prop.name);
if (attribute) {
prop.attribute = attribute.name || attribute.fieldName;
}
return prop.kind === 'field' && prop.privacy !== 'private';
});
allComponents.push({
...declaration,
methods,
properties
});
}
});
});
// Build dependency graphs
allComponents.forEach(component => {
const dependencies = [];
// Recursively fetch sub-dependencies
function getDependencies(tag) {
const cmp = allComponents.find(c => c.tagName === tag);
if (!cmp || !Array.isArray(component.dependencies)) {
return;
}
cmp.dependencies?.forEach(dependentTag => {
if (!dependencies.includes(dependentTag)) {
dependencies.push(dependentTag);
}
getDependencies(dependentTag);
});
}
getDependencies(component.tagName);
component.dependencies = dependencies.sort();
});
// Sort by name
return allComponents.sort((a, b) => {
if (a.name < b.name) return -1;
if (a.name > b.name) return 1;
return 0;
});
};

View File

@@ -0,0 +1,138 @@
let count = 1;
function escapeHtml(str) {
return String(str).replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;');
}
/**
* Turns code fields with the :preview suffix into interactive code previews.
*/
module.exports = function (doc, options) {
options = {
within: 'body', // the element containing the code fields to convert
...options
};
const within = doc.querySelector(options.within);
if (!within) {
return doc;
}
within.querySelectorAll('[class*=":preview"]').forEach(code => {
const pre = code.closest('pre');
if (!pre) {
return;
}
const adjacentPre = pre.nextElementSibling?.tagName.toLowerCase() === 'pre' ? pre.nextElementSibling : null;
const reactCode = adjacentPre?.querySelector('code[class$="react"]');
const sourceGroupId = `code-preview-source-group-${count}`;
const isExpanded = code.getAttribute('class').includes(':expanded');
const noCodePen = code.getAttribute('class').includes(':no-codepen');
count++;
const htmlButton = `
<button type="button"
title="Show HTML code"
class="code-preview__button code-preview__button--html"
>
HTML
</button>
`;
const reactButton = `
<button type="button" title="Show React code" class="code-preview__button code-preview__button--react">
React
</button>
`;
const codePenButton = `
<button type="button" class="code-preview__button code-preview__button--codepen" title="Edit on CodePen">
<svg
width="138"
height="26"
viewBox="0 0 138 26"
fill="none"
stroke="currentColor"
stroke-width="2.3"
stroke-linecap="round"
stroke-linejoin="round"
>
<path d="M80 6h-9v14h9 M114 6h-9 v14h9 M111 13h-6 M77 13h-6 M122 20V6l11 14V6 M22 16.7L33 24l11-7.3V9.3L33 2L22 9.3V16.7z M44 16.7L33 9.3l-11 7.4 M22 9.3l11 7.3 l11-7.3 M33 2v7.3 M33 16.7V24 M88 14h6c2.2 0 4-1.8 4-4s-1.8-4-4-4h-6v14 M15 8c-1.3-1.3-3-2-5-2c-4 0-7 3-7 7s3 7 7 7 c2 0 3.7-0.8 5-2 M64 13c0 4-3 7-7 7h-5V6h5C61 6 64 9 64 13z" />
</svg>
</button>
`;
const codePreview = `
<div class="code-preview ${isExpanded ? 'code-preview--expanded' : ''}">
<div class="code-preview__preview">
${code.textContent}
<div class="code-preview__resizer">
<sl-icon name="grip-vertical"></sl-icon>
</div>
</div>
<div class="code-preview__source-group" id="${sourceGroupId}">
<div class="code-preview__source code-preview__source--html" ${reactCode ? 'data-flavor="html"' : ''}>
<pre><code class="language-html">${escapeHtml(code.textContent)}</code></pre>
</div>
${
reactCode
? `
<div class="code-preview__source code-preview__source--react" data-flavor="react">
<pre><code class="language-jsx">${escapeHtml(reactCode.textContent)}</code></pre>
</div>
`
: ''
}
</div>
<div class="code-preview__buttons">
<button
type="button"
class="code-preview__button code-preview__toggle"
aria-expanded="${isExpanded ? 'true' : 'false'}"
aria-controls="${sourceGroupId}"
>
Source
<svg
viewBox="0 0 24 24"
fill="none"
stroke="currentColor"
stroke-width="2"
stroke-linecap="round"
stroke-linejoin="round"
>
<polyline points="6 9 12 15 18 9"></polyline>
</svg>
</button>
${reactCode ? ` ${htmlButton} ${reactButton} ` : ''}
${noCodePen ? '' : codePenButton}
</div>
</div>
`;
pre.insertAdjacentHTML('afterend', codePreview);
pre.remove();
if (adjacentPre) {
adjacentPre.remove();
}
});
// Wrap code preview scripts in anonymous functions so they don't run in the global scope
doc.querySelectorAll('.code-preview__preview script').forEach(script => {
if (script.type === 'module') {
// Modules are already scoped
script.textContent = script.innerHTML;
} else {
// Wrap non-modules in an anonymous function so they don't run in the global scope
script.textContent = `(() => { ${script.innerHTML} })();`;
}
});
return doc;
};

View File

@@ -0,0 +1,23 @@
let codeBlockId = 0;
/**
* Adds copy code buttons to code fields. The provided doc should be a document object provided by JSDOM. The same
* document will be returned with the appropriate DOM manipulations.
*/
module.exports = function (doc) {
doc.querySelectorAll('pre > code').forEach(code => {
const pre = code.closest('pre');
const button = doc.createElement('sl-copy-button');
if (!code.id) {
code.id = `code-block-${++codeBlockId}`;
}
button.classList.add('copy-code-button');
button.setAttribute('from', code.id);
pre.append(button);
});
return doc;
};

View File

@@ -0,0 +1,41 @@
const { isExternalLink } = require('./strings.cjs');
/**
* Transforms external links to make them safer and optionally add a target. The provided doc should be a document
* object provided by JSDOM. The same document will be returned with the appropriate DOM manipulations.
*/
module.exports = function (doc, options) {
options = {
className: 'external-link', // the class name to add to links
noopener: true, // sets rel="noopener"
noreferrer: true, // sets rel="noreferrer"
ignore: () => false, // callback function to filter links that should be ignored
within: 'body', // element that contains the target links
target: '', // sets the target attribute
...options
};
const within = doc.querySelector(options.within);
if (within) {
within.querySelectorAll('a').forEach(link => {
if (isExternalLink(link) && !options.ignore(link)) {
link.classList.add(options.className);
const rel = [];
if (options.noopener) rel.push('noopener');
if (options.noreferrer) rel.push('noreferrer');
if (rel.length) {
link.setAttribute('rel', rel.join(' '));
}
if (options.target) {
link.setAttribute('target', options.target);
}
}
});
}
return doc;
};

View File

@@ -0,0 +1,63 @@
const Prism = require('prismjs');
const PrismLoader = require('prismjs/components/index.js');
PrismLoader('diff');
PrismLoader.silent = true;
/** Highlights a code string. */
function highlight(code, language) {
const alias = language.replace(/^diff-/, '');
const isDiff = /^diff-/i.test(language);
// Auto-load the target language
if (!Prism.languages[alias]) {
PrismLoader(alias);
if (!Prism.languages[alias]) {
throw new Error(`Unsupported language for code highlighting: "${language}"`);
}
}
// Register diff-* languages to use the diff grammar
if (isDiff) {
Prism.languages[language] = Prism.languages.diff;
}
return Prism.highlight(code, Prism.languages[language], language);
}
/**
* Highlights all code fields that have a language parameter. If the language has a colon in its name, the first chunk
* will be the language used and additional chunks will be applied as classes to the `<pre>`. For example, a code field
* tagged with "html:preview" will be rendered as `<pre class="language-html preview">`.
*
* The provided doc should be a document object provided by JSDOM. The same document will be returned with the
* appropriate DOM manipulations.
*/
module.exports = function (doc) {
doc.querySelectorAll('pre > code[class]').forEach(code => {
// Look for class="language-*" and split colons into separate classes
code.classList.forEach(className => {
if (className.startsWith('language-')) {
//
// We use certain suffixes to indicate code previews, expanded states, etc. The class might look something like
// this:
//
// class="language-html:preview:expanded"
//
// The language will always come first, so we need to drop the "language-" prefix and everything after the first
// color to get the highlighter language.
//
const language = className.replace(/^language-/, '').split(':')[0];
try {
code.innerHTML = highlight(code.textContent ?? '', language);
} catch (err) {
// Language not found, skip it
}
}
});
});
return doc;
};

View File

@@ -0,0 +1,67 @@
const MarkdownIt = require('markdown-it');
const markdownItContainer = require('markdown-it-container');
const markdownItIns = require('markdown-it-ins');
const markdownItKbd = require('markdown-it-kbd');
const markdownItMark = require('markdown-it-mark');
const markdownItReplaceIt = require('markdown-it-replace-it');
const markdown = MarkdownIt({
html: true,
xhtmlOut: false,
breaks: false,
langPrefix: 'language-',
linkify: false,
typographer: false
});
// Third-party plugins
markdown.use(markdownItContainer);
markdown.use(markdownItIns);
markdown.use(markdownItKbd);
markdown.use(markdownItMark);
markdown.use(markdownItReplaceIt);
// Callouts
['tip', 'warning', 'danger'].forEach(type => {
markdown.use(markdownItContainer, type, {
render: function (tokens, idx) {
if (tokens[idx].nesting === 1) {
return `<div role="alert" class="callout callout--${type}">`;
}
return '</div>\n';
}
});
});
// Asides
markdown.use(markdownItContainer, 'aside', {
render: function (tokens, idx) {
if (tokens[idx].nesting === 1) {
return `<aside>`;
}
return '</aside>\n';
}
});
// Details
markdown.use(markdownItContainer, 'details', {
validate: params => params.trim().match(/^details\s+(.*)$/),
render: (tokens, idx) => {
const m = tokens[idx].info.trim().match(/^details\s+(.*)$/);
if (tokens[idx].nesting === 1) {
return `<details>\n<summary><span>${markdown.utils.escapeHtml(m[1])}</span></summary>\n`;
}
return '</details>\n';
}
});
// Replace [#1234] with a link to GitHub issues
markdownItReplaceIt.replacements.push({
name: 'github-issues',
re: /\[#([0-9]+)\]/gs,
sub: '<a href="https://github.com/shoelace-style/shoelace/issues/$1">#$1</a>',
html: true,
default: true
});
module.exports = markdown;

View File

@@ -0,0 +1,26 @@
const { format } = require('prettier');
/** Formats markup using prettier. */
module.exports = function (content, options) {
options = {
arrowParens: 'avoid',
bracketSpacing: true,
htmlWhitespaceSensitivity: 'css',
insertPragma: false,
bracketSameLine: false,
jsxSingleQuote: false,
parser: 'html',
printWidth: 120,
proseWrap: 'preserve',
quoteProps: 'as-needed',
requirePragma: false,
semi: true,
singleQuote: true,
tabWidth: 2,
trailingComma: 'none',
useTabs: false,
...options
};
return format(content, options);
};

View File

@@ -0,0 +1,19 @@
/**
* @typedef {object} Replacement
* @property {string | RegExp} pattern
* @property {string} replacement
*/
/**
* @typedef {Array<Replacement>} Replacements
*/
/**
* @param {Document} content
* @param {Replacements} replacements
*/
module.exports = function (content, replacements) {
replacements.forEach(replacement => {
content.body.innerHTML = content.body.innerHTML.replaceAll(replacement.pattern, replacement.replacement);
});
};

View File

@@ -0,0 +1,21 @@
/**
* Turns headings into clickable, deep linkable anchors. The provided doc should be a document object provided by JSDOM.
* The same document will be returned with the appropriate DOM manipulations.
*/
module.exports = function (doc, options) {
const tables = [...doc.querySelectorAll('table')];
options = {
className: 'table-scroll', // the class name to add to the table's container
...options
};
tables.forEach(table => {
const div = doc.createElement('div');
div.classList.add(options.className);
table.insertAdjacentElement('beforebegin', div);
div.append(table);
});
return doc;
};

View File

@@ -0,0 +1,16 @@
const slugify = require('slugify');
/** Creates a slug from an arbitrary string of text. */
module.exports.createSlug = function (text) {
return slugify(String(text), {
remove: /[^\w|\s]/g,
lower: true
});
};
/** Determines whether or not a link is external. */
module.exports.isExternalLink = function (link) {
// We use the "internal" hostname when initializing JSDOM so we know that those are local links
if (!link.hostname || link.hostname === 'internal') return false;
return true;
};

View File

@@ -0,0 +1,42 @@
/**
* Generates an in-page table of contents based on headings.
*/
module.exports = function (doc, options) {
options = {
levels: ['h2'], // headings to include (they must have an id)
container: 'nav', // the container to append links to
listItem: true, // if true, links will be wrapped in <li>
within: 'body', // the element containing the headings to summarize
...options
};
const container = doc.querySelector(options.container);
const within = doc.querySelector(options.within);
const headingSelector = options.levels.map(h => `${h}[id]`).join(', ');
if (!container || !within) {
return doc;
}
within.querySelectorAll(headingSelector).forEach(heading => {
const listItem = doc.createElement('li');
const link = doc.createElement('a');
const level = heading.tagName.slice(1);
link.href = `#${heading.id}`;
link.textContent = heading.textContent;
if (options.listItem) {
// List item + link
listItem.setAttribute('data-level', level);
listItem.append(link);
container.append(listItem);
} else {
// Link only
link.setAttribute('data-level', level);
container.append(link);
}
});
return doc;
};

View File

@@ -0,0 +1,23 @@
const smartquotes = require('smartquotes');
smartquotes.replacements.push([/---/g, '\u2014']); // em dash
smartquotes.replacements.push([/--/g, '\u2013']); // en dash
smartquotes.replacements.push([/\.\.\./g, '\u2026']); // ellipsis
smartquotes.replacements.push([/\(c\)/gi, '\u00A9']); // copyright
smartquotes.replacements.push([/\(r\)/gi, '\u00AE']); // registered trademark
smartquotes.replacements.push([/\?!/g, '\u2048']); // ?!
smartquotes.replacements.push([/!!/g, '\u203C']); // !!
smartquotes.replacements.push([/\?\?/g, '\u2047']); // ??
smartquotes.replacements.push([/([0-9]\s?)-(\s?[0-9])/g, '$1\u2013$2']); // number ranges use en dash
/**
* Improves typography by adding smart quotes and similar corrections within the specified element(s).
*
* The provided doc should be a document object provided by JSDOM. The same document will be returned with the
* appropriate DOM manipulations.
*/
module.exports = function (doc, selector = 'body') {
const elements = [...doc.querySelectorAll(selector)];
elements.forEach(el => smartquotes.element(el));
return doc;
};

Binary file not shown.

After

Width:  |  Height:  |  Size: 91 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 69 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 100 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 53 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 175 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 688 KiB

View File

@@ -0,0 +1,11 @@
<svg width="733" xmlns="http://www.w3.org/2000/svg" height="733">
<circle cy="366.5" cx="366.5" r="366.5"/>
<circle cy="366.5" cx="366.5" r="336.5" fill="#fede58"/>
<path d="M325 665c-121-21-194-115-212-233v-8l-25-1-1-18h481c6 13 10 27 13 41 13 94-38 146-114 193-45 23-93 29-142 26z"/>
<path d="M372 647c52-6 98-28 138-62 28-25 46-56 51-87 4-20 1-57-5-70l-423-1c-2 56 39 118 74 157 31 34 72 54 116 63 11 2 38 2 49 0z" fill="#871945"/>
<path d="M76 342c-13-26-13-57-9-85 6-27 18-52 35-68 21-20 50-23 77-18 15 4 28 12 39 23 18 17 30 40 36 67 4 20 4 41 0 60l-6 21z"/>
<path d="M234 323c5-6 6-40 2-58-3-16-4-16-10-10-14 14-38 14-52 0-15-18-12-41 6-55 3-3 5-5 5-6-1-4-22-8-34-7-42 4-57.6 40-66.2 77-3 17-1 53 4 59H234z" fill="#fff"/>
<path d="M378 343c-2-3-6-20-7-29-5-28-1-57 11-83 15-30 41-52 72-60 29-7 57 0 82 15 26 17 45 49 50 82 2 12 2 33 0 45-1 10-5 26-8 30z"/>
<path d="M565 324c4-5 5-34 4-50-2-14-6-24-8-24-1 0-3 2-6 5-17 17-47 13-58-9-7-16-4-31 8-43 4-4 7-8 7-9 0 0-4-2-8-3-51-17-105 20-115 80-3 15 0 43 3 53z" fill="#fff"/>
<path d="M504 590s-46 40-105 53c-66 15-114-7-114-7s14-76 93-95c76-18 126 49 126 49z" fill="#f9bedd"/>
</svg>

After

Width:  |  Height:  |  Size: 1.1 KiB

View File

@@ -0,0 +1,23 @@
<svg width="160" height="45" fill="none" xmlns="http://www.w3.org/2000/svg">
<g filter="url(#filter0_d)">
<rect x="2" y="2" width="156" height="40" rx="16" fill="#F9F9F9"/>
<path fill-rule="evenodd" clip-rule="evenodd" d="M30.425 11.174c.604 1.114.233 2.53-.83 3.164l-6.986 4.166a.378.378 0 00-.18.325v6.748c0 .134.069.258.18.325l5.714 3.407c.11.066.244.066.354 0l5.714-3.407a.378.378 0 00.18-.325V21.29l-4.986 2.936c-1.067.628-2.416.231-3.015-.886-.6-1.118-.22-2.532.846-3.16l7.008-4.127c2.048-1.206 4.576.345 4.576 2.806v6.718c0 1.803-.924 3.467-2.42 4.36l-5.713 3.407a4.596 4.596 0 01-4.734 0l-5.714-3.408C18.924 29.044 18 27.38 18 25.576V18.83c0-1.803.924-3.467 2.42-4.36l6.985-4.165c1.063-.634 2.415-.245 3.02.87z" fill="url(#paint0_linear)"/>
<path fill="#F9F9F9" d="M47 12.5h95v-1H47z"/>
<path d="M52.538 27.752c2.744 0 4.844-1.876 4.844-5.152 0-3.108-2.1-5.152-4.844-5.152s-4.802 2.002-4.802 5.152c0 3.29 2.058 5.152 4.802 5.152zm0-1.554c-1.736 0-2.912-1.316-2.912-3.598 0-2.226 1.162-3.598 2.912-3.598s2.954 1.4 2.954 3.598c0 2.31-1.218 3.598-2.954 3.598zm7.89 4.158V27.22c0-.196-.013-.378-.055-.658.434.7 1.022 1.19 2.17 1.19 1.736 0 3.066-1.414 3.066-3.626 0-2.17-1.19-3.682-2.996-3.682-1.078 0-1.806.476-2.24 1.204.042-.28.056-.462.056-.672v-.308H58.72v9.688h1.708zm1.695-3.948c-1.036 0-1.764-.938-1.764-2.31 0-1.414.742-2.296 1.764-2.296 1.092 0 1.75.952 1.75 2.296 0 1.372-.7 2.31-1.75 2.31zm7.866 1.344c1.848 0 3.052-1.078 3.192-2.478h-1.736c-.112.714-.714 1.134-1.456 1.134-1.036 0-1.722-.826-1.736-1.904h4.97v-.378c0-2.226-1.204-3.682-3.29-3.682-1.988 0-3.43 1.47-3.43 3.626 0 2.366 1.442 3.682 3.486 3.682zm-1.75-4.48c.098-.896.756-1.554 1.68-1.554.924 0 1.526.63 1.554 1.554H68.24zm8.006 4.228v-4.004c0-.952.616-1.694 1.456-1.694.798 0 1.288.63 1.288 1.638v4.06h1.708v-4.312c0-1.68-.896-2.744-2.408-2.744-1.078 0-1.722.518-2.1 1.204.042-.266.056-.476.056-.672v-.308h-1.708V27.5h1.708zm8.911-7.868h1.792V17.84h-1.792v1.792zm.042 1.036V27.5h1.708v-6.832h-1.708zm5.097 6.832v-4.004c0-.952.616-1.694 1.456-1.694.798 0 1.288.63 1.288 1.638v4.06h1.708v-4.312c0-1.68-.896-2.744-2.408-2.744-1.078 0-1.722.518-2.1 1.204.042-.266.056-.476.056-.672v-.308h-1.708V27.5h1.708zm13.238.252c1.526 0 2.52-.658 2.982-1.54-.07.322-.098.644-.098.98v.308h1.68v-5.222h-4.34v1.554h2.66v.07c0 1.4-1.134 2.296-2.59 2.296-1.792 0-3.024-1.372-3.024-3.598s1.26-3.598 3.066-3.598c1.302 0 2.17.756 2.296 1.736h1.89c-.182-1.904-1.764-3.29-4.214-3.29-2.954 0-4.928 2.128-4.928 5.152 0 3.136 1.848 5.152 4.62 5.152zm6.063-8.12h1.792V17.84h-1.792v1.792zm.042 1.036V27.5h1.708v-6.832h-1.708zm6.413 6.958c.434 0 .84-.07 1.008-.126v-1.288c-.168.028-.35.042-.518.042-.728 0-1.008-.42-1.008-1.134v-3.094h1.68v-1.358h-1.68v-2.464h-1.708v2.464h-1.554v1.358h1.554v3.346c0 1.526.77 2.254 2.226 2.254zm3.961 2.73V27.22c0-.196-.014-.378-.056-.658.434.7 1.022 1.19 2.17 1.19 1.736 0 3.066-1.414 3.066-3.626 0-2.17-1.19-3.682-2.996-3.682-1.078 0-1.806.476-2.24 1.204.042-.28.056-.462.056-.672v-.308h-1.708v9.688h1.708zm1.694-3.948c-1.036 0-1.764-.938-1.764-2.31 0-1.414.742-2.296 1.764-2.296 1.092 0 1.75.952 1.75 2.296 0 1.372-.7 2.31-1.75 2.31zm7.88 1.344c2.058 0 3.514-1.372 3.514-3.64 0-2.24-1.456-3.668-3.514-3.668-2.044 0-3.5 1.428-3.5 3.668 0 2.268 1.442 3.64 3.5 3.64zm0-1.344c-1.064 0-1.764-.84-1.764-2.296 0-1.484.728-2.31 1.764-2.31 1.05 0 1.778.826 1.778 2.31 0 1.456-.714 2.296-1.778 2.296zm7.551 1.344c1.26 0 1.876-.686 2.142-1.19-.056.238-.056.42-.056.658v.28h1.708v-9.8h-1.708v3.276c0 .21 0 .42.056.672-.392-.658-1.05-1.204-2.114-1.204-1.596 0-3.15 1.218-3.15 3.668 0 2.408 1.316 3.64 3.122 3.64zm.406-1.344c-1.022 0-1.792-.896-1.792-2.31 0-1.358.77-2.296 1.792-2.296s1.778.896 1.778 2.296c0 1.372-.756 2.31-1.778 2.31z" fill="#12100C"/>
</g>
<defs>
<linearGradient id="paint0_linear" x1="33.806" y1="13.629" x2="22.389" y2="30.86" gradientUnits="userSpaceOnUse">
<stop stop-color="#FFB45B"/>
<stop offset="1" stop-color="#FF8A00"/>
</linearGradient>
<filter id="filter0_d" x="0" y=".5" width="160" height="44" filterUnits="userSpaceOnUse" color-interpolation-filters="sRGB">
<feFlood flood-opacity="0" result="BackgroundImageFix"/>
<feColorMatrix in="SourceAlpha" values="0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0"/>
<feOffset dy=".5"/>
<feGaussianBlur stdDeviation="1"/>
<feColorMatrix values="0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.1 0"/>
<feBlend in2="BackgroundImageFix" result="effect1_dropShadow"/>
<feBlend in="SourceGraphic" in2="effect1_dropShadow" result="shape"/>
</filter>
</defs>
</svg>

After

Width:  |  Height:  |  Size: 4.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 29 KiB

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.3 KiB

After

Width:  |  Height:  |  Size: 7.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 55 KiB

After

Width:  |  Height:  |  Size: 55 KiB

View File

@@ -41,7 +41,7 @@
<ellipse id="Oval" fill="#2F2E41" fill-rule="nonzero" cx="103.34581" cy="426.732" rx="10.90314" ry="4.08868"></ellipse>
<circle id="Oval" fill="#FFFFFF" fill-rule="nonzero" cx="86.99113" cy="358.86008" r="14.71922"></circle>
<circle id="Oval" fill="#3F3D56" fill-rule="nonzero" cx="86.99113" cy="358.86008" r="4.90642"></circle>
<path d="M44.12401,329.71183 C40.64653,314.13804 51.76268,298.4014 68.95262,294.56302 C86.14256,290.72464 102.89683,300.23813 106.37431,315.81192 C109.85179,331.38571 98.45939,337.12961 81.26945,340.96792 C64.07951,344.80623 47.60154,345.28568 44.12401,329.71183 Z" id="Path" fill="#E6E6E6" fill-rule="nonzero"></path>
<path d="M44.12401,329.71183 C40.64653,314.13804 51.76268,298.4014 68.95262,294.56302 C86.14256,290.72464 102.89683,300.23813 106.37431,315.81192 C109.85179,331.38571 98.45939,337.12961 81.26945,340.96792 C64.07951,344.80623 47.60154,345.28568 44.12401,329.71183 Z" id="Path" fill="#12a5e9" fill-rule="nonzero"></path>
<ellipse id="Oval" fill="#2F2E41" fill-rule="nonzero" transform="translate(110.988725, 213.490755) rotate(-69.082170) translate(-110.988725, -213.490755) " cx="110.988725" cy="213.490755" rx="21.53369" ry="6.76007"></ellipse>
<circle id="Oval" fill="#2F2E41" fill-rule="nonzero" transform="translate(71.181568, 246.012788) rotate(-80.782520) translate(-71.181568, -246.012788) " cx="71.1815681" cy="246.012788" r="43.06735"></circle>
<rect id="Rectangle" fill="#2F2E41" fill-rule="nonzero" x="51.55595" y="279.81244" width="13.08374" height="23.44171"></rect>
@@ -53,7 +53,7 @@
<path d="M29.40483,205.96134 C25.92735,190.38755 37.0435,174.65088 54.23344,170.8125 C71.42338,166.97412 88.17766,176.48758 91.65513,192.06138 C95.1326,207.63518 83.74022,213.37903 66.55028,217.21738 C49.36034,221.05573 32.88231,221.53519 29.40483,205.96134 Z" id="Path" fill="#0ea5e9" fill-rule="nonzero"></path>
<ellipse id="Oval" fill="#2F2E41" fill-rule="nonzero" transform="translate(22.673401, 226.029366) rotate(-64.625740) translate(-22.673401, -226.029366) " cx="22.6734006" cy="226.029366" rx="6.76007" ry="21.53368"></ellipse>
<path d="M50.02702,261.54972 C50.02702,265.76487 60.88029,274.08829 72.92357,274.08829 C84.96685,274.08829 96.25871,262.22129 96.25871,258.0062 C96.25871,253.79111 84.96678,258.82395 72.92357,258.82395 C60.88036,258.82395 50.02702,257.33457 50.02702,261.54972 Z" id="Path" fill="#FFFFFF" fill-rule="nonzero"></path>
<path d="M113.52376,81.56869 C111.867655,81.5704977 110.525568,82.9125851 110.52376,84.56869 L110.52376,208.56869 C110.525568,210.224795 111.867655,211.566882 113.52376,211.56869 L400.52376,211.56869 C402.179865,211.566882 403.521952,210.224795 403.52376,208.56869 L403.52376,84.56869 C403.521952,82.9125851 402.179865,81.5704977 400.52376,81.56869 L113.52376,81.56869 Z" id="Path" fill="#0ea5e9" fill-rule="nonzero"></path>
<path d="M113.52376,81.56869 C111.867655,81.5704977 110.525568,82.9125851 110.52376,84.56869 L110.52376,208.56869 C110.525568,210.224795 111.867655,211.566882 113.52376,211.56869 L400.52376,211.56869 C402.179865,211.566882 403.521952,210.224795 403.52376,208.56869 L403.52376,84.56869 C403.521952,82.9125851 402.179865,81.5704977 400.52376,81.56869 L113.52376,81.56869 Z" id="Path" fill="#fbc024" fill-rule="nonzero"></path>
<circle id="Oval" fill="#FFFFFF" fill-rule="nonzero" cx="191.01816" cy="146.56869" r="29.1211"></circle>
<path d="M256.7436,142.69417 C254.884983,142.724723 253.39428,144.240132 253.39428,146.099 C253.39428,147.957868 254.884983,149.473277 256.7436,149.50383 L348.68926,149.50383 C349.906316,149.524778 351.042001,148.894505 351.668119,147.850647 C352.294237,146.806789 352.31556,145.508108 351.72405,144.444258 C351.132539,143.380407 350.018157,142.713189 348.80107,142.69417 C348.763797,142.693537 348.726527,142.693537 348.68926,142.69417 L256.7436,142.69417 Z" id="b71acdfd-6a55-428e-917a-53f192cb0203" fill="#FFFFFF" fill-rule="nonzero"></path>
<path d="M256.7436,122.96697 C254.884983,122.997523 253.39428,124.512932 253.39428,126.3718 C253.39428,128.230668 254.884983,129.746077 256.7436,129.77663 L302.65917,129.77663 C303.876249,129.797613 305.011971,129.167347 305.638111,128.123473 C306.26425,127.0796 306.285572,125.78089 305.694037,124.717025 C305.102503,123.65316 303.988082,122.985951 302.77097,122.96697 C302.733703,122.966337 302.696437,122.966337 302.65917,122.96697 L256.7436,122.96697 Z" id="ad4fbcfa-41b0-45f9-a593-23b6dc3fe165" fill="#FFFFFF" fill-rule="nonzero"></path>
@@ -67,13 +67,13 @@
<circle id="Oval" fill="#3F3D56" fill-rule="nonzero" cx="725.31949" cy="403.22896" r="4.90642"></circle>
<ellipse id="Oval" fill="#2F2E41" fill-rule="nonzero" transform="translate(771.918005, 384.148727) rotate(-53.549900) translate(-771.918005, -384.148727) " cx="771.918005" cy="384.148727" rx="21.53368" ry="6.76007"></ellipse>
<path d="M705.39698,436.33866 C705.39698,432.86466 714.34198,426.00466 724.26778,426.00466 C734.19358,426.00466 743.50006,435.78516 743.50006,439.25914 C743.50006,442.73312 734.19351,438.58514 724.26778,438.58514 C714.34205,438.58514 705.39698,439.81268 705.39698,436.33866 Z" id="Path" fill="#FFFFFF" fill-rule="nonzero" transform="translate(724.448520, 433.325266) rotate(-180.000000) translate(-724.448520, -433.325266) "></path>
<path d="M847.1767,378.54172 L611.43117,345.86064 C607.604361,345.32541 604.932725,341.793834 605.45868,337.96574 L631.96057,146.79396 C632.495641,142.967058 636.027329,140.295337 639.85547,140.82147 L875.60098,173.50256 C879.427885,174.037626 882.099609,177.569318 881.57347,181.39746 L855.0716,372.56924 C854.536375,376.396051 851.004794,379.067687 847.1767,378.54172 L847.1767,378.54172 Z" id="Path" fill="#0ea5e9" fill-rule="nonzero"></path>
<path d="M847.1767,378.54172 L611.43117,345.86064 C607.604361,345.32541 604.932725,341.793834 605.45868,337.96574 L631.96057,146.79396 C632.495641,142.967058 636.027329,140.295337 639.85547,140.82147 L875.60098,173.50256 C879.427885,174.037626 882.099609,177.569318 881.57347,181.39746 L855.0716,372.56924 C854.536375,376.396051 851.004794,379.067687 847.1767,378.54172 L847.1767,378.54172 Z" id="Path" fill="#9358ff" fill-rule="nonzero"></path>
<path d="M762.72231,318.87957 L642.36784,302.19498 C642.216871,302.176045 642.067969,302.14324 641.92302,302.09698 L712.51355,211.39072 C713.394132,210.238632 714.82651,209.649483 716.262854,209.8486 C717.699198,210.047717 718.917295,211.004295 719.45127,212.35248 L748.48059,283.8148 L749.87186,287.23459 L762.72231,318.87957 Z" id="Path" fill="#FFFFFF" fill-rule="nonzero"></path>
<polygon id="Path" fill="#000000" fill-rule="nonzero" opacity="0.2" points="762.722 318.879 721.63 313.183 745.864 286.679 747.609 284.77 748.481 283.815 749.872 287.235"></polygon>
<path d="M829.73481,328.16942 L725.63807,313.73863 L749.87186,287.23463 L751.61612,285.32515 L783.19533,250.78503 C784.29885,249.735613 785.796059,249.204111 787.314261,249.322828 C788.832463,249.441546 790.228856,250.199316 791.15584,251.40751 C791.271244,251.575507 791.375823,251.750689 791.46894,251.93199 L829.73481,328.16942 Z" id="Path" fill="#FFFFFF" fill-rule="nonzero"></path>
<circle id="Oval" fill="#FFFFFF" fill-rule="nonzero" cx="764.18602" cy="224.18353" r="18"></circle>
<rect id="Rectangle" fill="#3F3D56" fill-rule="nonzero" transform="translate(653.262165, 167.923576) rotate(7.892770) translate(-653.262165, -167.923576) " x="642.262129" y="156.923541" width="22.0000711" height="22.0000711"></rect>
<path d="M768.18655,374.08068 C771.66403,358.50689 760.54788,342.77022 743.35794,338.93184 C726.168,335.09346 709.41373,344.60692 705.93625,360.18071 C702.45877,375.7545 713.85117,381.49837 731.04111,385.33671 C748.23105,389.17505 764.70908,389.6545 768.18655,374.08068 Z" id="Path" fill="#F2F2F2" fill-rule="nonzero"></path>
<rect id="Rectangle" fill="#FFFFFF" fill-rule="nonzero" transform="translate(653.262165, 167.923576) rotate(7.892770) translate(-653.262165, -167.923576) " x="642.262129" y="156.923541" width="22.0000711" height="22.0000711"></rect>
<path d="M768.18655,374.08068 C771.66403,358.50689 760.54788,342.77022 743.35794,338.93184 C726.168,335.09346 709.41373,344.60692 705.93625,360.18071 C702.45877,375.7545 713.85117,381.49837 731.04111,385.33671 C748.23105,389.17505 764.70908,389.6545 768.18655,374.08068 Z" id="Path" fill="#12a5e9" fill-rule="nonzero"></path>
<ellipse id="Oval" fill="#2F2E41" fill-rule="nonzero" transform="translate(735.010556, 473.249892) rotate(-4.181640) translate(-735.010556, -473.249892) " cx="735.010556" cy="473.249892" rx="10.90314" ry="4.08868"></ellipse>
</g>
</g>

Before

Width:  |  Height:  |  Size: 19 KiB

After

Width:  |  Height:  |  Size: 19 KiB

View File

@@ -0,0 +1,32 @@
<svg width="673" height="739" viewBox="0 0 673 739" xmlns="http://www.w3.org/2000/svg">
<g fill-rule="nonzero" fill="none">
<path d="M467 149.805c-46.62-7.44-99.71-11.41-155-11.41-50.6 0-99.35 3.32-142.98 9.58.01-.67.02-1.34.05-2.01C171.475 65.082 237.996.903 318.914 1.398c80.917.494 146.649 65.48 148.066 146.387.01.68.02 1.35.02 2.02Z" fill="#0BA5E9"/>
<path d="M337.55 1.342a149.047 149.047 0 0 0-168.93 143.229c-.031.67-.04 1.34-.05 2.01 12.961-1.86 26.384-3.454 40.164-4.784 3.478-71.745 57.64-130.8 128.816-140.455Z" opacity=".1" fill="#FFF"/>
<path d="M532.18 161.625a600.121 600.121 0 0 0-65.2-13.84 943.364 943.364 0 0 0-108.74-10.45 1133.608 1133.608 0 0 0-83.01-.34 973.29 973.29 0 0 0-106.16 8.97 624.292 624.292 0 0 0-77.25 15.66C32.61 177.995 0 199.935 0 223.395s32.61 45.4 91.82 61.77c41.64 11.52 92.98 19.37 148.92 22.97 23.09 1.5 46.96 2.26 71.26 2.26 24.38 0 48.33-.77 71.49-2.27 50.91-3.29 98.01-10.1 137.43-20 .21-.06.41-.11.62-.16 2.66-.66 5.28-1.35 7.87-2.04.93-.26 1.85-.51 2.77-.76a.978.978 0 0 1 .16-.05c.88-.24 1.75-.49 2.62-.73 1.74-.5 3.46-.99 5.15-1.5.08-.02.15-.04.22-.06 1.47-.44 2.91-.88 4.34-1.32 1.17-.37 2.33-.73 3.48-1.1.84-.27 1.67-.54 2.49-.81.6-.2 1.19-.39 1.77-.59.79-.26 1.58-.53 2.36-.8.33-.11.66-.22.98-.34.75-.25 1.48-.51 2.21-.77.79-.28 1.58-.57 2.36-.85.65-.23 1.3-.47 1.94-.71.54-.21 1.07-.41 1.61-.61 1.47-.55 2.91-1.12 4.33-1.68.71-.29 1.42-.57 2.12-.86.69-.28 1.39-.57 2.07-.86 1.12-.47 2.22-.94 3.3-1.41.52-.24 1.05-.47 1.56-.69.39-.18.77-.35 1.16-.53.28-.12.56-.25.83-.38 1.01-.46 2.01-.93 2.99-1.4 3.76-1.8 7.27-3.64 10.53-5.52 20.45-11.71 31.24-24.7 31.24-38.2 0-23.46-32.61-45.4-91.82-61.77Zm-.54 121.62c-41.69 11.53-93.17 19.38-149.26 22.95-22.81 1.45-46.39 2.2-70.38 2.2-23.91 0-47.41-.74-70.15-2.19-56.18-3.56-107.74-11.41-149.49-22.96C34.09 267.125 2 245.875 2 223.395c0-1.986.252-3.965.74-5.89 5.1-20.28 36.47-39.26 89.62-53.96a623.806 623.806 0 0 1 76.66-15.57 976.027 976.027 0 0 1 106.8-9c11.92-.39 23.98-.583 36.18-.58 15.41 0 30.65.31 45.63.91a941.367 941.367 0 0 1 109.37 10.5 598.858 598.858 0 0 1 64.64 13.74c53.14 14.7 84.5 33.67 89.61 53.94.496 1.93.75 3.916.75 5.91 0 22.48-32.09 43.73-90.36 59.85Z" fill="#3F3D56"/>
<path d="M623.43 224.305c0 13.36-11.01 26-30.67 37.29-3.27 1.88-6.79 3.72-10.53 5.52-.98.47-1.98.94-2.99 1.4-.27.13-.55.26-.83.38-.39.18-.77.35-1.16.53-.51.22-1.04.45-1.56.69-1.08.47-2.18.94-3.3 1.41-.68.29-1.38.58-2.07.86-.7.29-1.41.57-2.12.86-1.42.56-2.86 1.13-4.33 1.68-.54.2-1.07.4-1.61.61-.64.24-1.29.48-1.94.71-.78.28-1.57.57-2.36.85-.73.26-1.46.52-2.21.77-.32.12-.65.23-.98.34-.78.27-1.57.54-2.36.8-.58.2-1.17.39-1.77.59-.82.27-1.65.54-2.49.81-1.15.37-2.31.73-3.48 1.1-1.43.44-2.87.88-4.34 1.32-.07.02-.14.04-.22.06-1.69.51-3.41 1-5.15 1.5-.87.24-1.74.49-2.62.73a.978.978 0 0 0-.16.05c-.92.25-1.84.5-2.77.76-2.58.68-5.21 1.37-7.87 2.04-.21.05-.41.1-.62.16-38.35 9.58-85.4 16.56-137.47 19.93-22.81 1.47-46.59 2.25-71.02 2.25-24.65 0-48.63-.79-71.62-2.29-137.24-8.95-239.38-43.03-239.38-83.71.01-2.475.388-4.936 1.12-7.3.06.17.12.33.19.5 14.27 37.48 115.54 67.77 246.94 75.16 20.13 1.14 40.98 1.73 62.32 1.73 21.43 0 42.36-.6 62.57-1.74 131.29-7.42 232.46-37.72 246.68-75.17.24-.6.45-1.2.63-1.8a25.304 25.304 0 0 1 1.55 8.62ZM91.67 213.54c-16.643 0-34.331-3.58-34.331-10.216 0-6.636 17.688-10.217 34.33-10.217 16.643 0 34.331 3.58 34.331 10.217 0 6.636-17.688 10.217-34.33 10.217Zm0-18.433c-19.054 0-32.331 4.33-32.331 8.217 0 3.886 13.277 8.217 32.33 8.217 19.053 0 32.331-4.33 32.331-8.217 0-3.886-13.278-8.217-32.33-8.217Z" fill="#3F3D56"/>
<path d="M162.67 260.54c-16.643 0-34.331-3.58-34.331-10.216 0-6.636 17.688-10.217 34.33-10.217 16.643 0 34.331 3.58 34.331 10.217 0 6.636-17.688 10.217-34.33 10.217Zm0-18.433c-19.054 0-32.331 4.33-32.331 8.217 0 3.886 13.277 8.217 32.33 8.217 19.053 0 32.331-4.33 32.331-8.217 0-3.886-13.278-8.217-32.33-8.217ZM531.67 213.54c-16.643 0-34.331-3.58-34.331-10.216 0-6.636 17.688-10.217 34.33-10.217 16.643 0 34.331 3.58 34.331 10.217 0 6.636-17.688 10.217-34.33 10.217Zm0-18.433c-19.054 0-32.331 4.33-32.331 8.217 0 3.886 13.277 8.217 32.33 8.217 19.053 0 32.331-4.33 32.331-8.217 0-3.886-13.278-8.217-32.33-8.217ZM460.67 260.54c-16.643 0-34.331-3.58-34.331-10.216 0-6.636 17.688-10.217 34.33-10.217 16.643 0 34.331 3.58 34.331 10.217 0 6.636-17.688 10.217-34.33 10.217Zm0-18.433c-19.054 0-32.331 4.33-32.331 8.217 0 3.886 13.277 8.217 32.33 8.217 19.053 0 32.331-4.33 32.331-8.217 0-3.886-13.278-8.217-32.33-8.217ZM311.67 282.54c-16.643 0-34.331-3.58-34.331-10.216 0-6.636 17.688-10.217 34.33-10.217 16.643 0 34.331 3.58 34.331 10.217 0 6.636-17.688 10.217-34.33 10.217Zm0-18.433c-19.054 0-32.331 4.33-32.331 8.217 0 3.886 13.277 8.217 32.33 8.217 19.053 0 32.331-4.33 32.331-8.217 0-3.886-13.278-8.217-32.33-8.217Z" fill="#3F3D56"/>
<circle fill="#2F2E41" cx="336.978" cy="450.705" r="42.012"/>
<path fill="#2F2E41" d="m300.555 488.547 20.447-10.24 5.715 11.413-20.447 10.24z"/>
<ellipse fill="#2F2E41" transform="rotate(-56.601 300.086 492.946)" cx="300.086" cy="492.946" rx="3.989" ry="10.636"/>
<path fill="#2F2E41" d="m347.239 489.72 5.715-11.412 20.447 10.24-5.715 11.412z"/>
<ellipse fill="#2F2E41" transform="rotate(-33.399 373.87 492.946)" cx="373.87" cy="492.946" rx="10.636" ry="3.989"/>
<circle fill="#FFF" cx="334.037" cy="440.429" r="14.359"/>
<ellipse fill="#3F3D56" transform="rotate(-45 334.135 434.282)" cx="334.135" cy="434.282" rx="4.766" ry="4.8"/>
<path d="M370.12 405c.632-15.553-12.773-28.727-29.941-29.425-17.168-.697-31.597 11.346-32.229 26.9-.632 15.553 11.302 19.087 28.47 19.785 17.167.697 33.068-1.706 33.7-17.26Z" fill="#0BA5E9"/>
<ellipse fill="#2F2E41" transform="rotate(-40.645 380.654 456.766)" cx="380.654" cy="456.766" rx="6.594" ry="21.006"/>
<ellipse fill="#2F2E41" transform="rotate(-49.355 293.42 456.766)" cx="293.419" cy="456.766" rx="21.006" ry="6.594"/>
<path d="M348.517 467.262a9.572 9.572 0 1 1-18.836 3.428l-.003-.018c-.942-5.202 3.08-7.043 8.282-7.985 5.203-.942 9.615-.628 10.557 4.575Z" fill="#FFF"/>
<path d="M266 495.395a2 2 0 0 1-2-2v-118a2 2 0 0 1 4 0v118a2 2 0 0 1-2 2ZM236 601.395a2 2 0 0 1-2-2v-86a2 2 0 0 1 4 0v86a2 2 0 0 1-2 2ZM313 530.395a2 2 0 0 1-2-2v-118a2 2 0 0 1 4 0v118a2 2 0 0 1-2 2ZM284 615.395a2 2 0 0 1-2-2v-48a2 2 0 0 1 4 0v48a2 2 0 0 1-2 2ZM325 369.395a2 2 0 0 1-2-2v-48a2 2 0 0 1 4 0v48a2 2 0 0 1-2 2ZM225 390.395a2 2 0 0 1-2-2v-48a2 2 0 0 1 4 0v48a2 2 0 0 1-2 2ZM399 395.395a2 2 0 0 1-2-2v-48a2 2 0 0 1 4 0v48a2 2 0 0 1-2 2ZM395 545.395a2 2 0 0 1-2-2v-58a2 2 0 0 1 4 0v58a2 2 0 0 1-2 2ZM355 596.395a2 2 0 0 1-2-2v-86a2 2 0 0 1 4 0v86a2 2 0 0 1-2 2ZM363 449.395a2 2 0 0 1-2-2v-118a2 2 0 0 1 4 0v118a2 2 0 0 1-2 2Z" fill="#CCC"/>
<ellipse fill="#2F2E41" transform="rotate(-39.938 594.37 683.981)" cx="594.369" cy="683.981" rx="6.76" ry="21.534"/>
<circle fill="#2F2E41" transform="rotate(-71.565 548.562 676.503)" cx="548.562" cy="676.503" r="43.067"/>
<path fill="#2F2E41" d="M553.707 710.303h13.084v23.442h-13.084zM527.54 710.303h13.084v23.442H527.54z"/>
<ellipse fill="#2F2E41" cx="555.888" cy="734.017" rx="10.903" ry="4.089"/>
<ellipse fill="#2F2E41" cx="529.72" cy="733.472" rx="10.903" ry="4.089"/>
<path d="M535.04 622.366c3.845-15.487 20.82-24.6 37.914-20.356 17.094 4.245 27.834 20.24 23.989 35.727-3.846 15.487-16.604 15.537-33.698 11.293-17.094-4.245-32.051-11.177-28.206-26.664Z" fill="#0BA5E9"/>
<ellipse fill="#2F2E41" transform="rotate(-64.626 500.054 656.52)" cx="500.054" cy="656.52" rx="6.76" ry="21.534"/>
<circle fill="#FFF" cx="542.124" cy="667.416" r="14.359"/>
<circle fill="#3F3D56" cx="536.222" cy="662.269" r="4.786"/>
<circle fill="#FFF" cx="542" cy="697.395" r="6"/>
<path d="M671.531 738.395h-236a1 1 0 1 1 0-2h236a1 1 0 0 1 0 2Z" fill="#3F3D56"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.6 KiB

View File

@@ -1,203 +0,0 @@
.code-block {
position: relative;
border-radius: 3px;
background-color: rgb(var(--sl-color-neutral-50));
margin-bottom: 1.5rem;
}
.code-block__preview {
position: relative;
border: solid 1px rgb(var(--sl-color-neutral-200));
border-bottom: none;
border-top-left-radius: 3px;
border-top-right-radius: 3px;
background-color: rgb(var(--sl-color-neutral-0));
min-width: 20rem;
max-width: 100%;
padding: 1.5rem 3.25rem 1.5rem 1.5rem;
}
/* Block the preview while dragging to prevent iframes from intercepting drag events */
.code-block__preview--dragging:after {
content: '';
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
opacity: 0;
cursor: ew-resize;
}
.code-block__resizer {
display: flex;
align-items: center;
justify-content: center;
position: absolute;
top: 0;
right: 0;
bottom: 0;
width: 1.75rem;
font-size: 20px;
color: rgb(var(--sl-color-neutral-600));
background-color: rgb(var(--sl-color-neutral-0));
border-left: solid 1px rgb(var(--sl-color-neutral-200));
border-top-right-radius: 3px;
cursor: ew-resize;
transition: 250ms background-color;
}
@media screen and (max-width: 600px) {
.code-block__preview {
padding-right: 1.5rem;
}
.code-block__resizer {
display: none;
}
}
.code-block__source {
border: solid 1px rgb(var(--sl-color-neutral-200));
border-bottom: none;
border-radius: 0 !important;
margin: 0;
display: none;
}
.code-block--expanded .code-block__source {
display: block;
}
.code-block__buttons {
position: relative;
border: solid 1px rgb(var(--sl-color-neutral-200));
border-bottom-left-radius: 3px;
border-bottom-right-radius: 3px;
display: flex;
}
.code-block__button {
flex: 0 0 auto;
height: 2.5rem;
min-width: 2.5rem;
border: none;
border-radius: 0;
background: rgb(var(--sl-color-neutral-0));
font: inherit;
font-size: 0.7rem;
font-weight: 500;
text-transform: uppercase;
color: rgb(var(--sl-color-neutral-600));
padding: 0 1rem;
cursor: pointer;
}
.code-block__button:not(:last-of-type) {
border-right: solid 1px rgb(var(--sl-color-neutral-200));
}
.code-block__button--codepen {
display: flex;
place-items: center;
width: 6rem;
}
.code-block__button:first-of-type {
border-bottom-left-radius: 3px;
}
.code-block__button:last-of-type {
border-bottom-right-radius: 3px;
}
.code-block__button:hover,
.code-block__button:active {
box-shadow: 0 0 0 1px rgb(var(--sl-color-primary-400));
border-right-color: transparent;
background-color: rgb(var(--sl-color-primary-50));
color: rgb(var(--sl-color-primary-700));
z-index: 1;
}
.code-block__button:focus-visible {
outline: none;
color: rgb(var(--sl-color-primary-600));
border-color: rgb(var(--sl-color-primary-400));
border-right-color: transparent;
background-color: rgb(var(--sl-color-primary-50));
box-shadow: 0 0 0 1px rgb(var(--sl-color-primary-400)), var(--sl-focus-ring);
z-index: 2;
}
.code-block__toggle {
position: relative;
display: flex;
flex: 1 1 auto;
align-items: center;
justify-content: center;
width: 100%;
color: rgb(var(--sl-color-neutral-600));
cursor: pointer;
-webkit-appearance: none;
}
.code-block__toggle svg {
width: 1em;
height: 1em;
margin-left: 0.25rem;
}
.code-block--expanded .code-block__toggle svg {
transform: rotate(180deg);
}
/* Copy button styles */
.markdown-section .docsify-copy-code-button {
top: 4px;
right: 4px;
background-color: rgb(var(--sl-color-neutral-600));
border-radius: var(--sl-border-radius-medium);
font-family: var(--sl-font-sans);
font-size: var(--sl-font-size-x-small);
font-weight: var(--sl-font-weight-semibold);
text-transform: uppercase;
padding: 8px;
user-select: none;
transition: 0.1s all;
}
.markdown-section .docsify-copy-code-button.copied {
animation: pulse 0.75s;
--pulse-color: rgb(var(--sl-color-neutral-600));
}
@keyframes pulse {
0% {
box-shadow: 0 0 0 0 var(--pulse-color);
}
70% {
box-shadow: 0 0 0 0.5rem transparent;
}
100% {
box-shadow: 0 0 0 0 transparent;
}
}
.markdown-section .docsify-copy-code-button .label {
transition: none;
}
.markdown-section .docsify-copy-code-button .success,
.markdown-section .docsify-copy-code-button .error {
display: none;
}
.markdown-section .docsify-copy-code-button:focus-visible {
box-shadow: 0 0 0 3px rgb(var(--sl-color-neutral-500) / 50%);
}
.markdown-section .docsify-copy-code-button:active {
background-color: rgb(var(--sl-color-neutral-600));
transform: scale(0.92);
}

View File

@@ -1,208 +0,0 @@
(() => {
let count = 1;
if (!window.$docsify) {
throw new Error('Docsify must be loaded before installing this plugin.');
}
function runScript(script) {
const newScript = document.createElement('script');
if (script.type === 'module') {
newScript.type = 'module';
newScript.textContent = script.innerHTML;
} else {
newScript.appendChild(document.createTextNode(`(() => { ${script.innerHTML} })();`));
}
script.parentNode.replaceChild(newScript, script);
}
function wrap(el, wrapper) {
el.parentNode.insertBefore(wrapper, el);
wrapper.appendChild(el);
}
window.$docsify.plugins.push((hook, vm) => {
// Convert code blocks to previews
hook.afterEach(function (html, next) {
const domParser = new DOMParser();
const doc = domParser.parseFromString(html, 'text/html');
const codePenButton = `
<button type="button" class="code-block__button code-block__button--codepen" title="Edit on CodePen">
<svg
width="138"
height="26"
viewBox="0 0 138 26"
fill="none"
stroke="currentColor"
stroke-width="2.3"
stroke-linecap="round"
stroke-linejoin="round"
>
<path d="M80 6h-9v14h9 M114 6h-9 v14h9 M111 13h-6 M77 13h-6 M122 20V6l11 14V6 M22 16.7L33 24l11-7.3V9.3L33 2L22 9.3V16.7z M44 16.7L33 9.3l-11 7.4 M22 9.3l11 7.3 l11-7.3 M33 2v7.3 M33 16.7V24 M88 14h6c2.2 0 4-1.8 4-4s-1.8-4-4-4h-6v14 M15 8c-1.3-1.3-3-2-5-2c-4 0-7 3-7 7s3 7 7 7 c2 0 3.7-0.8 5-2 M64 13c0 4-3 7-7 7h-5V6h5C61 6 64 9 64 13z" />
</svg>
</button>
`;
[...doc.querySelectorAll('code[class^="lang-"]')].map(code => {
if (code.classList.contains('preview')) {
const pre = code.closest('pre');
const preId = `code-block-preview-${count}`;
const toggleId = `code-block-toggle-${count}`;
pre.id = preId;
pre.classList.add('code-block__source');
pre.setAttribute('data-lang', pre.getAttribute('data-lang').replace(/ preview$/, ''));
pre.setAttribute('aria-labelledby', toggleId);
const codeBlock = `
<div class="code-block">
<div class="code-block__preview">
${code.textContent}
<div class="code-block__resizer">
<sl-icon name="grip-vertical"></sl-icon>
</div>
</div>
${pre.outerHTML}
<div class="code-block__buttons">
<button type="button" class="code-block__button code-block__toggle" aria-expanded="false" aria-controls="${preId}">
View Source
<svg
viewBox="0 0 24 24"
fill="none"
stroke="currentColor"
stroke-width="2"
stroke-linecap="round"
stroke-linejoin="round"
>
<polyline points="6 9 12 15 18 9"></polyline>
</svg>
</button>
${!code.classList.contains('no-codepen') ? codePenButton : ''}
</div>
</div>
`;
pre.replaceWith(domParser.parseFromString(codeBlock, 'text/html').body);
count++;
}
});
next(doc.body.innerHTML);
});
// After the page is done loading, force scripts in previews to execute
hook.doneEach(() => {
[...document.querySelectorAll('.code-block__preview script')].map(script => runScript(script));
});
// Horizontal resizing
hook.doneEach(() => {
[...document.querySelectorAll('.code-block__preview')].map(preview => {
const resizer = preview.querySelector('.code-block__resizer');
let startX;
let startWidth;
const dragStart = event => {
startX = event.changedTouches ? event.changedTouches[0].pageX : event.clientX;
startWidth = parseInt(document.defaultView.getComputedStyle(preview).width, 10);
preview.classList.add('code-block__preview--dragging');
event.preventDefault();
document.documentElement.addEventListener('mousemove', dragMove, false);
document.documentElement.addEventListener('touchmove', dragMove, false);
document.documentElement.addEventListener('mouseup', dragStop, false);
document.documentElement.addEventListener('touchend', dragStop, false);
};
const dragMove = event => {
setWidth(startWidth + (event.changedTouches ? event.changedTouches[0].pageX : event.pageX) - startX);
};
const dragStop = event => {
preview.classList.remove('code-block__preview--dragging');
document.documentElement.removeEventListener('mousemove', dragMove, false);
document.documentElement.removeEventListener('touchmove', dragMove, false);
document.documentElement.removeEventListener('mouseup', dragStop, false);
document.documentElement.removeEventListener('touchend', dragStop, false);
};
const setWidth = width => (preview.style.width = width + 'px');
resizer.addEventListener('mousedown', dragStart);
resizer.addEventListener('touchstart', dragStart);
}, false);
});
});
// Open in CodePen
document.addEventListener('click', event => {
const button = event.target.closest('button');
if (button?.classList.contains('code-block__button--codepen')) {
const codeBlock = button.closest('.code-block');
const html = codeBlock.querySelector('.code-block__source > code').textContent;
const version = sessionStorage.getItem('sl-version');
const form = document.createElement('form');
form.action = 'https://codepen.io/pen/define';
form.method = 'POST';
form.target = '_blank';
// Docs: https://blog.codepen.io/documentation/prefill/
const data = {
title: '',
description: '',
tags: ['shoelace', 'web components'],
editors: '100',
head: `<meta name="viewport" content="width=device-width">`,
css_external: ``,
js_external: ``,
js_module: true,
html:
`<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@${version}/dist/themes/light.css">\n` +
`<script type="module" src="https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@${version}/dist/shoelace.js"></script>\n` +
`\n` +
html,
css: `body {\n font: 16px sans-serif;\n}`,
js: ``
};
const input = document.createElement('input');
input.type = 'hidden';
input.name = 'data';
input.value = JSON.stringify(data);
form.append(input);
document.body.append(form);
form.submit();
form.remove();
}
});
// Expand and collapse code blocks
document.addEventListener('click', event => {
const toggle = event.target.closest('.code-block__toggle');
if (toggle) {
const codeBlock = event.target.closest('.code-block');
codeBlock.classList.toggle('code-block--expanded');
event.target.setAttribute('aria-expanded', codeBlock.classList.contains('code-block--expanded'));
}
});
// Show pulse when copying
document.addEventListener('click', event => {
const button = event.target.closest('.docsify-copy-code-button');
if (button) {
button.classList.remove('copied');
requestAnimationFrame(() => {
button.addEventListener('animationend', () => button.classList.remove('copied'), { once: true });
button.classList.add('copied');
});
}
});
})();

View File

@@ -1,512 +0,0 @@
(() => {
const isDev = location.hostname === 'localhost';
const isNext = location.hostname === 'next.shoelace.style';
const customElements = fetch('/dist/custom-elements.json')
.then(res => res.json())
.catch(err => console.error(err));
function createPropsTable(props) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
<th>Reflects</th>
<th>Type</th>
<th>Default</th>
</tr>
</thead>
<tbody>
${props
.map(prop => {
const hasAttribute = !!prop.attribute;
const isAttributeDifferent = prop.attribute !== prop.name;
let attributeInfo = '';
if (!hasAttribute) {
attributeInfo = `<br><small>(property only)</small>`;
} else if (isAttributeDifferent) {
attributeInfo = `
<br>
<sl-tooltip content="This attribute is different than the property">
<small>
<code class="nowrap">
${escapeHtml(prop.attribute)}
</code>
</small>
</sl-tooltip>`;
}
return `
<tr>
<td>
<code class="nowrap">${escapeHtml(prop.name)}</code>
${attributeInfo}
</td>
<td>
${escapeHtml(prop.description)}
</td>
<td style="text-align: center;">${
prop.reflects ? '<sl-icon label="yes" name="check"></sl-icon>' : ''
}</td>
<td>${prop.type?.text ? `<code>${escapeHtml(prop.type?.text || '')}</code>` : '-'}</td>
<td>${prop.default ? `<code>${escapeHtml(prop.default)}</code>` : '-'}</td>
</tr>
`;
})
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createEventsTable(events) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
<th>Event Detail</th>
</tr>
</thead>
<tbody>
${events
.map(
event => `
<tr>
<td><code class="nowrap">${escapeHtml(event.name)}</code></td>
<td>${escapeHtml(event.description)}</td>
<td>${event.type?.text ? `<code>${escapeHtml(event.type?.text)}` : '-'}</td>
</tr>
`
)
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createMethodsTable(methods) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
<th>Arguments</th>
</tr>
</thead>
<tbody>
${methods
.map(
method => `
<tr>
<td class="nowrap"><code>${escapeHtml(method.name)}</code></td>
<td>${escapeHtml(method.description)}</td>
<td>
${
method.parameters?.length
? `
<code>${escapeHtml(
method.parameters.map(param => `${param.name}: ${param.type.text}`).join(', ')
)}</code>
`
: '-'
}
</td>
</tr>
`
)
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createSlotsTable(slots) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
</tr>
</thead>
<tbody>
${slots
.map(
slot => `
<tr>
<td class="nowrap">${slot.name ? `<code>${escapeHtml(slot.name)}</code>` : '(default)'}</td>
<td>${escapeHtml(slot.description)}</td>
</tr>
`
)
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createCustomPropertiesTable(styles) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
</tr>
</thead>
<tbody>
${styles
.map(
style => `
<tr>
<td><code>${escapeHtml(style.name)}</code></td>
<td>${escapeHtml(style.description)}</td>
</tr>
`
)
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createPartsTable(parts) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
</tr>
</thead>
<tbody>
${parts
.map(
part => `
<tr>
<td class="nowrap"><code>${escapeHtml(part.name)}</code></td>
<td>${escapeHtml(part.description)}</td>
</tr>
`
)
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createAnimationsTable(animations) {
const table = document.createElement('table');
table.innerHTML = `
<thead>
<tr>
<th>Name</th>
<th>Description</th>
</tr>
</thead>
<tbody>
${animations
.map(
animation => `
<tr>
<td class="nowrap"><code>${escapeHtml(animation.name)}</code></td>
<td>${escapeHtml(animation.description)}</td>
</tr>
`
)
.join('')}
</tbody>
`;
return table.outerHTML;
}
function createDependenciesList(targetComponent, allComponents) {
const ul = document.createElement('ul');
const dependencies = [];
// Recursively fetch subdependencies
function getDependencies(tag) {
const component = allComponents.find(c => c.tagName === tag);
if (!component || !Array.isArray(component.dependencies)) {
return [];
}
component.dependencies?.map(tag => {
if (!dependencies.includes(tag)) {
dependencies.push(tag);
}
getDependencies(tag);
});
}
getDependencies(targetComponent);
dependencies.sort().map(tag => {
const li = document.createElement('li');
li.innerHTML = `<code>&lt;${tag}&gt;</code>`;
ul.appendChild(li);
});
return ul.outerHTML;
}
function escapeHtml(html) {
return (html + '')
.replace(/&/g, '&amp;')
.replace(/</g, '&lt;')
.replace(/>/g, '&gt;')
.replace(/"/g, '&quot;')
.replace(/'/g, '&apos;')
.replace(/`(.*?)`/g, '<code>$1</code>');
}
function getAllComponents(metadata) {
const allComponents = [];
metadata.modules?.map(module => {
module.declarations?.map(declaration => {
if (declaration.customElement) {
// Generate the dist path based on the src path and attach it to the component
declaration.path = module.path.replace(/^src\//, 'dist/').replace(/\.ts$/, '.js');
allComponents.push(declaration);
}
});
});
return allComponents;
}
function getComponent(metadata, tagName) {
return getAllComponents(metadata).find(component => component.tagName === tagName);
}
if (!window.$docsify) {
throw new Error('Docsify must be loaded before installing this plugin.');
}
window.$docsify.plugins.push((hook, vm) => {
hook.mounted(async function () {
const metadata = await customElements;
const target = document.querySelector('.app-name');
// Add version
const version = document.createElement('div');
version.classList.add('sidebar-version');
version.textContent = isDev ? 'Development' : isNext ? 'Next' : metadata.package.version;
target.appendChild(version);
// Store version for reuse
sessionStorage.setItem('sl-version', metadata.package.version);
// Add repo buttons
const buttons = document.createElement('div');
buttons.classList.add('sidebar-buttons');
buttons.innerHTML = `
<sl-button size="small" class="repo-button repo-button--sponsor" href="https://github.com/sponsors/claviska" target="_blank">
<sl-icon name="heart"></sl-icon> Sponsor
</sl-button>
<sl-button size="small" class="repo-button repo-button--github" href="https://github.com/shoelace-style/shoelace/stargazers" target="_blank">
<sl-icon name="github"></sl-icon> <span class="github-star-count">Star</span>
</sl-button>
<sl-button size="small" class="repo-button repo-button--twitter" href="https://twitter.com/shoelace_style" target="_blank">
<sl-icon name="twitter"></sl-icon> Follow
</sl-button>
`;
target.appendChild(buttons);
});
hook.beforeEach(async function (content, next) {
const metadata = await customElements;
// Replace %VERSION% placeholders
content = content.replace(/%VERSION%/g, metadata.package.version);
// Handle [component-header] tags
content = content.replace(/\[component-header:([a-z-]+)\]/g, (match, tag) => {
const component = getComponent(metadata, tag);
let result = '';
if (!component) {
console.error('Component not found in metadata: ' + tag);
return next(content);
}
let badgeType = 'neutral';
if (component.status === 'stable') badgeType = 'primary';
if (component.status === 'experimental') badgeType = 'warning';
if (component.status === 'planned') badgeType = 'neutral';
if (component.status === 'deprecated') badgeType = 'danger';
result += `
<div class="component-header">
<div class="component-header__tag">
<code>&lt;${component.tagName}&gt; | ${component.name}</code>
</div>
<div class="component-header__info">
<sl-badge type="neutral" pill>
Since ${component.since || '?'}
</sl-badge>
<sl-badge type="${badgeType}" pill style="text-transform: capitalize;">
${component.status}
</sl-badge>
</div>
</div>
`;
return result.replace(/^ +| +$/gm, '');
});
// Handle [component-metadata] tags
content = content.replace(/\[component-metadata:([a-z-]+)\]/g, (match, tag) => {
const component = getComponent(metadata, tag);
let result = '';
if (!component) {
console.error('Component not found in metadata: ' + tag);
return next(content);
}
// Remove members that are private or don't have a description
const members = component.members?.filter(member => member.description && member.privacy !== 'private');
const methods = members?.filter(prop => prop.kind === 'method' && prop.privacy !== 'private');
const props = members?.filter(prop => {
// Look for a corresponding attribute
const attribute = component.attributes?.find(attr => attr.fieldName === prop.name);
if (attribute) {
prop.attribute = attribute.name || attribute.fieldName;
}
return prop.kind === 'field' && prop.privacy !== 'private';
});
if (props?.length) {
result += `
## Properties
${createPropsTable(props)}
`;
}
if (component.events?.length) {
result += `
## Events
${createEventsTable(component.events)}
`;
}
if (methods?.length) {
result += `
## Methods
${createMethodsTable(methods)}
`;
}
if (component.slots?.length) {
result += `
## Slots
${createSlotsTable(component.slots)}
`;
}
if (component.cssProperties?.length) {
result += `
## CSS Custom Properties
${createCustomPropertiesTable(component.cssProperties)}
`;
}
if (component.cssParts?.length) {
result += `
## CSS Parts
${createPartsTable(component.cssParts)}
`;
}
if (component.animations?.length) {
result += `
## Animations
${createAnimationsTable(component.animations)}
Learn how to [customize animations](/getting-started/customizing#animations).
`;
}
if (component.dependencies?.length) {
result += `
## Dependencies
This component imports the following dependencies.
${createDependenciesList(component.tagName, getAllComponents(metadata))}
`;
}
if (component.path) {
/* prettier-ignore */
result += `
## Importing
<sl-tab-group>
<sl-tab slot="nav" panel="cdn" active>CDN</sl-tab>
<sl-tab slot="nav" panel="bundler">Bundler</sl-tab>
<sl-tab slot="nav" panel="react">React</sl-tab>
<sl-tab-panel name="cdn">\n
To import this component from [the CDN](https://www.jsdelivr.com/package/npm/@shoelace-style/shoelace):
\`\`\`js
import 'https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@${metadata.package.version}/${component.path}';
\`\`\`
</sl-tab-panel>
<sl-tab-panel name="bundler">\n
To import this component using [a bundler](/getting-started/installation#bundling):
\`\`\`js
import '@shoelace-style/shoelace/${component.path}';
\`\`\`
</sl-tab-panel>
<sl-tab-panel name="react">\n
To import this component using [\`@shoelace-style/react\`](https://www.npmjs.com/package/@shoelace-style/react):
\`\`\`js
import '@shoelace-style/react/dist/${component.tagName.replace(/^sl-/, '')}';
\`\`\`
</sl-tab-panel>
</sl-tab-group>
`;
}
// Strip whitespace so markdown doesn't process things as code blocks
return result.replace(/^ +| +$/gm, '');
});
next(content);
});
// Wrap tables so we can scroll them horizontally when needed
hook.doneEach(function () {
const content = document.querySelector('.content');
const tables = [...content.querySelectorAll('table')];
tables.map(table => {
table.outerHTML = `
<div class="table-wrapper">
${table.outerHTML}
</div>
`;
});
});
});
})();

View File

@@ -1,24 +0,0 @@
(() => {
if (!window.$docsify) {
throw new Error('Docsify must be loaded before installing this plugin.');
}
//
// Docsify generates pages dynamically and asynchronously, so when a reload happens, the scroll position can't be
// be restored immediately. This plugin waits until Docsify loads the page and then restores it.
//
window.$docsify.plugins.push((hook, vm) => {
hook.ready(() => {
// Restore
const scrollTop = sessionStorage.getItem('bs-scroll');
if (scrollTop) {
document.documentElement.scrollTop = scrollTop;
}
// Remember
document.addEventListener('scroll', event => {
sessionStorage.setItem('bs-scroll', document.documentElement.scrollTop);
});
});
});
})();

File diff suppressed because it is too large Load Diff

View File

@@ -1,172 +0,0 @@
body.site-search-visible {
overflow: hidden;
}
.sidebar .search-box {
margin: 1.25rem 26px;
}
.sidebar .search-box kbd {
margin-top: 2px;
}
/* Site search */
.site-search {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
z-index: 1000;
}
.site-search[hidden] {
display: none;
}
.site-search__overlay {
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: rgb(var(--sl-overlay-background-color) / var(--sl-overlay-opacity));
z-index: -1;
}
.site-search__panel {
display: flex;
flex-direction: column;
max-width: 460px;
max-height: calc(100vh - 20rem);
background-color: rgb(var(--sl-surface-base-alt));
border-radius: var(--sl-border-radius-large);
box-shadow: var(--sl-shadow-x-large);
margin: 10rem auto;
}
@media screen and (max-width: 900px) {
.site-search__panel {
max-width: 100%;
max-height: calc(92vh - 120px); /* allow iOS browser chrome */
margin: 4vh var(--sl-spacing-medium);
}
}
.site-search__input::part(base) {
border: none;
background: transparent;
border-radius: var(--sl-border-radius-large);
}
.site-search__input:focus-within::part(base) {
outline: none;
box-shadow: none;
}
.site-search__input {
--sl-input-height-large: 4rem;
}
.site-search__body {
flex: 1 1 auto;
overflow: auto;
}
.site-search--has-results .site-search__body {
border-top: solid 1px rgb(var(--sl-color-neutral-200));
}
.site-search__results {
display: none;
line-height: var(--sl-line-height-dense);
list-style: none;
padding: var(--sl-spacing-x-small) 0;
margin: 0;
}
.site-search--has-results .site-search__results {
display: block;
}
.site-search__results a {
display: block;
text-decoration: none;
padding: var(--sl-spacing-x-small) var(--sl-spacing-large);
}
.site-search__results li a:hover,
.site-search__results li a:hover small {
background-color: rgb(var(--sl-color-neutral-100));
}
.site-search__results li[aria-selected='true'] a,
.site-search__results li[aria-selected='true'] a small,
.site-search__results li[aria-selected='true'] a sl-icon {
outline: none;
color: rgb(var(--sl-color-neutral-0));
background-color: rgb(var(--sl-color-primary-600));
}
.site-search__results h3 {
font-weight: var(--sl-font-weight-semibold);
margin: 0;
}
.site-search__results small {
display: block;
color: rgb(var(--sl-color-neutral-600));
}
.site-search__result {
padding: 0;
margin: 0;
}
.site-search__result a {
display: flex;
align-items: center;
gap: var(--sl-spacing-medium);
}
.site-search__result-icon {
flex: 0 0 auto;
display: flex;
color: rgb(var(--sl-color-neutral-400));
font-size: var(--sl-font-size-x-large);
}
.site-search__result-description {
flex: 1 1 auto;
}
.site-search__empty {
display: none;
border-top: solid 1px rgb(var(--sl-color-neutral-200));
text-align: center;
padding: var(--sl-spacing-x-large);
}
.site-search--no-results .site-search__empty {
display: block;
}
.site-search__footer {
display: flex;
justify-content: center;
gap: var(--sl-spacing-large);
border-top: solid 1px rgb(var(--sl-color-neutral-200));
border-bottom-left-radius: inherit;
border-bottom-right-radius: inherit;
padding: var(--sl-spacing-medium);
}
.site-search__footer small {
color: rgb(var(--sl-color-neutral-700));
}
@media screen and (max-width: 900px) {
.site-search__footer {
display: none;
}
}

View File

@@ -1,293 +0,0 @@
(() => {
if (!window.$docsify) {
throw new Error('Docsify must be loaded before installing this plugin.');
}
window.$docsify.plugins.push((hook, vm) => {
// Append the search box to the sidebar
hook.mounted(function () {
const appName = document.querySelector('.sidebar .app-name');
const searchBox = document.createElement('div');
searchBox.classList.add('search-box');
searchBox.innerHTML = `
<sl-input
type="search"
placeholder="Search"
clearable
pill
>
<sl-icon slot="prefix" name="search"></sl-icon>
<kbd slot="suffix" title="Press / to search">/</kbd>
</sl-input>
`;
const searchBoxInput = searchBox.querySelector('sl-input');
appName.insertAdjacentElement('afterend', searchBox);
// Show the search panel when the search is clicked
searchBoxInput.addEventListener('mousedown', event => {
event.preventDefault();
show();
});
// Show the search panel when a key is pressed
searchBoxInput.addEventListener('keydown', event => {
if (event.key === 'Tab') {
return;
}
// Pass the character that was typed through to the search input
if (event.key.length === 1) {
event.preventDefault();
input.value = event.key;
show();
}
});
});
// Append the search panel to the body
const siteSearch = document.createElement('div');
siteSearch.classList.add('site-search');
siteSearch.hidden = true;
siteSearch.innerHTML = `
<div class="site-search__overlay"></div>
<div class="site-search__panel">
<header class="site-search__header">
<sl-input
class="site-search__input"
type="search"
placeholder="Search this site"
size="large"
clearable
>
<sl-icon slot="prefix" name="search"></sl-icon>
</sl-input>
</header>
<div class="site-search__body">
<ul class="site-search__results"></ul>
<div class="site-search__empty">No results found.</div>
</div>
<footer class="site-search__footer">
<small><kbd>↑</kbd> <kbd>↓</kbd> navigate</small>
<small><kbd>↲</kbd> select</small>
<small><kbd>esc</kbd> close</small>
</footer>
</div>
`;
document.body.append(siteSearch);
const searchButtons = [...document.querySelectorAll('[data-site-search]')];
const overlay = siteSearch.querySelector('.site-search__overlay');
const panel = siteSearch.querySelector('.site-search__panel');
const input = siteSearch.querySelector('.site-search__input');
const results = siteSearch.querySelector('.site-search__results');
const animationDuration = 150;
const searchDebounce = 200;
let isShowing = false;
let searchTimeout;
let searchIndex;
let map;
// Load search data
const searchData = fetch('../../../search.json')
.then(res => res.json())
.then(data => {
searchIndex = lunr.Index.load(data.searchIndex);
map = data.map;
});
async function show() {
isShowing = true;
document.body.classList.add('site-search-visible');
siteSearch.hidden = false;
input.focus();
updateResults();
await Promise.all([
panel.animate(
[
{ opacity: 0, transform: 'scale(.9)' },
{ opacity: 1, transform: 'scale(1)' }
],
{ duration: animationDuration }
).finished,
overlay.animate([{ opacity: 0 }, { opacity: 1 }], { duration: animationDuration }).finished
]);
document.addEventListener('mousedown', handleDocumentMouseDown);
document.addEventListener('keydown', handleDocumentKeyDown);
document.addEventListener('focusin', handleDocumentFocusIn);
}
async function hide() {
isShowing = false;
document.body.classList.remove('site-search-visible');
await Promise.all([
panel.animate(
[
{ opacity: 1, transform: 'scale(1)' },
{ opacity: 0, transform: 'scale(.9)' }
],
{ duration: animationDuration }
).finished,
overlay.animate([{ opacity: 1 }, { opacity: 0 }], { duration: animationDuration }).finished
]);
siteSearch.hidden = true;
input.value = '';
updateResults();
document.removeEventListener('mousedown', handleDocumentMouseDown);
document.removeEventListener('keydown', handleDocumentKeyDown);
document.removeEventListener('focusin', handleDocumentFocusIn);
}
function handleInput() {
// Debounce search queries
clearTimeout(searchTimeout);
searchTimeout = setTimeout(() => updateResults(input.value), searchDebounce);
}
function handleDocumentFocusIn(event) {
// Close when focus leaves the panel
if (event.target.closest('.site-search__panel') !== panel) {
hide();
}
}
function handleDocumentMouseDown(event) {
// Close when clicking outside of the panel
if (event.target.closest('.site-search__overlay') === overlay) {
hide();
}
}
function handleDocumentKeyDown(event) {
// Close when pressing escape
if (event.key === 'Escape') {
event.preventDefault();
hide();
return;
}
// Handle keyboard selections
if (['ArrowDown', 'ArrowUp', 'Home', 'End', 'Enter'].includes(event.key)) {
event.preventDefault();
const currentEl = results.querySelector('[aria-selected="true"]');
const items = [...results.querySelectorAll('li')];
const index = items.indexOf(currentEl);
let nextEl;
if (items.length === 0) {
return;
}
switch (event.key) {
case 'ArrowUp':
nextEl = items[Math.max(0, index - 1)];
break;
case 'ArrowDown':
nextEl = items[Math.min(items.length - 1, index + 1)];
break;
case 'Home':
nextEl = items[0];
break;
case 'End':
nextEl = items[items.length - 1];
break;
case 'Enter':
currentEl?.querySelector('a')?.click();
break;
}
// Update the selected item
items.map(item => {
if (item === nextEl) {
item.setAttribute('aria-selected', 'true');
nextEl.scrollIntoView({ block: 'nearest' });
} else {
item.setAttribute('aria-selected', 'false');
}
});
return;
}
}
async function updateResults(query = '') {
try {
await searchIndex;
const hasQuery = query.length > 0;
let matches = hasQuery ? searchIndex.search(`${query}`) : [];
// Fall back to a fuzzy search if no matches are found
if (matches.length === 0 && hasQuery) {
matches = searchIndex.search(`${query}~2`);
}
let hasResults = hasQuery && matches.length > 0;
siteSearch.classList.toggle('site-search--has-results', hasQuery && hasResults);
siteSearch.classList.toggle('site-search--no-results', hasQuery && !hasResults);
panel.setAttribute('aria-expanded', hasQuery && hasResults ? 'true' : 'false');
results.innerHTML = '';
matches.map((match, index) => {
const page = map[match.ref];
const li = document.createElement('li');
const a = document.createElement('a');
let icon = 'file-text';
if (page.url.includes('getting-started/')) icon = 'lightbulb';
if (page.url.includes('resources/')) icon = 'book';
if (page.url.includes('components/')) icon = 'puzzle';
if (page.url.includes('tokens/')) icon = 'palette2';
if (page.url.includes('utilities/')) icon = 'wrench';
if (page.url.includes('tutorials/')) icon = 'joystick';
a.href = $docsify.routerMode === 'hash' ? `/#/${page.url}` : `/${page.url}`;
a.innerHTML = `
<div class="site-search__result-icon">
<sl-icon name="${icon}" aria-hidden="true"></sl-icon>
</div>
<div class="site-search__result__details">
<h3>${page.title}</h3>
<small>${page.url}</small>
</div>
`;
li.classList.add('site-search__result');
li.setAttribute('aria-selected', index === 0 ? 'true' : 'false');
li.appendChild(a);
results.appendChild(li);
});
} catch {
// Ignore query errors as the user types
}
}
// Show the search panel slash is pressed outside of a form element
document.addEventListener('keydown', event => {
if (
!isShowing &&
event.key === '/' &&
!event.composedPath().some(el => ['input', 'textarea'].includes(el?.tagName?.toLowerCase()))
) {
event.preventDefault();
show();
}
});
input.addEventListener('sl-input', handleInput);
// Close when a result is selected
results.addEventListener('click', event => {
if (event.target.closest('a')) {
hide();
}
});
});
})();

View File

@@ -1,29 +0,0 @@
.theme-picker {
position: fixed;
top: 1rem;
right: 1rem;
z-index: 30;
}
.theme-picker:not(:defined) {
display: none;
}
.theme-picker sl-menu-label {
white-space: nowrap;
}
.theme-picker sl-menu-label kbd {
margin-left: 0.5rem;
}
@media screen and (max-width: 768px) {
.theme-picker {
top: 0.5rem;
right: 0.5rem;
}
.theme-picker sl-menu-label {
display: none;
}
}

View File

@@ -1,84 +0,0 @@
(() => {
if (!window.$docsify) {
throw new Error('Docsify must be loaded before installing this plugin.');
}
window.$docsify.plugins.push((hook, vm) => {
hook.mounted(function () {
function getTheme() {
return localStorage.getItem('theme') || 'auto';
}
function isDark() {
if (theme === 'auto') {
return window.matchMedia('(prefers-color-scheme: dark)').matches;
} else {
return theme === 'dark';
}
}
function setTheme(newTheme) {
const noTransitions = Object.assign(document.createElement('style'), {
textContent: '* { transition: none !important; }'
});
theme = newTheme;
localStorage.setItem('theme', theme);
// Update the UI
[...menu.querySelectorAll('sl-menu-item')].map(item => (item.checked = item.getAttribute('value') === theme));
menuIcon.name = isDark() ? 'moon' : 'sun';
// Toggle the dark mode class without transitions
document.body.appendChild(noTransitions);
requestAnimationFrame(() => {
document.documentElement.classList.toggle('sl-theme-dark', isDark());
requestAnimationFrame(() => document.body.removeChild(noTransitions));
});
}
let theme = getTheme();
// Generate the theme picker dropdown
const dropdown = document.createElement('sl-dropdown');
dropdown.classList.add('theme-picker');
dropdown.innerHTML = `
<sl-button size="small" pill slot="trigger" caret>
<sl-icon name="sun" label="Select Theme"></sl-icon>
</sl-button>
<sl-menu>
<sl-menu-label>Toggle <kbd>\\</kbd></sl-menu-label>
<sl-menu-item value="light">Light</sl-menu-item>
<sl-menu-item value="dark">Dark</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item value="auto">Auto</sl-menu-item>
</sl-menu>
`;
document.querySelector('.sidebar-toggle').insertAdjacentElement('afterend', dropdown);
// Listen for selections
const menu = dropdown.querySelector('sl-menu');
const menuIcon = dropdown.querySelector('sl-icon');
menu.addEventListener('sl-select', event => setTheme(event.detail.item.value));
// Update the theme when the preference changes
window.matchMedia('(prefers-color-scheme: dark)').addListener(event => setTheme(theme));
// Toggle themes when pressing backslash
document.addEventListener('keydown', event => {
if (
event.key === '\\' &&
!event.composedPath().some(el => ['input', 'textarea'].includes(el?.tagName?.toLowerCase()))
) {
event.preventDefault();
setTheme(isDark() ? 'light' : 'dark');
show();
}
});
// Set the intial theme and sync the UI
setTheme(theme);
});
});
})();

View File

@@ -0,0 +1,249 @@
(() => {
function convertModuleLinks(html) {
html = html
.replace(/@shoelace-style\/shoelace/g, `https://esm.sh/@shoelace-style/shoelace@${shoelaceVersion}`)
.replace(/from 'react'/g, `from 'https://esm.sh/react@${reactVersion}'`)
.replace(/from "react"/g, `from "https://esm.sh/react@${reactVersion}"`);
return html;
}
function getAdjacentExample(name, pre) {
let currentPre = pre.nextElementSibling;
while (currentPre?.tagName.toLowerCase() === 'pre') {
if (currentPre?.getAttribute('data-lang').split(' ').includes(name)) {
return currentPre;
}
currentPre = currentPre.nextElementSibling;
}
return null;
}
function runScript(script) {
const newScript = document.createElement('script');
if (script.type === 'module') {
newScript.type = 'module';
newScript.textContent = script.innerHTML;
} else {
newScript.appendChild(document.createTextNode(`(() => { ${script.innerHTML} })();`));
}
script.parentNode.replaceChild(newScript, script);
}
function getFlavor() {
return sessionStorage.getItem('flavor') || 'html';
}
function setFlavor(newFlavor) {
flavor = ['html', 'react'].includes(newFlavor) ? newFlavor : 'html';
sessionStorage.setItem('flavor', flavor);
// Set the flavor class on the body
document.documentElement.classList.toggle('flavor-html', flavor === 'html');
document.documentElement.classList.toggle('flavor-react', flavor === 'react');
}
function syncFlavor() {
setFlavor(getFlavor());
document.querySelectorAll('.code-preview__button--html').forEach(preview => {
if (flavor === 'html') {
preview.classList.add('code-preview__button--selected');
}
});
document.querySelectorAll('.code-preview__button--react').forEach(preview => {
if (flavor === 'react') {
preview.classList.add('code-preview__button--selected');
}
});
}
const shoelaceVersion = document.documentElement.getAttribute('data-shoelace-version');
const reactVersion = '18.2.0';
const cdndir = 'cdn';
const npmdir = 'dist';
let flavor = getFlavor();
let count = 1;
// We need the version to open
if (!shoelaceVersion) {
throw new Error('The data-shoelace-version attribute is missing from <html>.');
}
// Sync flavor UI on page load
syncFlavor();
//
// Resizing previews
//
document.addEventListener('mousedown', handleResizerDrag);
document.addEventListener('touchstart', handleResizerDrag, { passive: true });
function handleResizerDrag(event) {
const resizer = event.target.closest('.code-preview__resizer');
const preview = event.target.closest('.code-preview__preview');
if (!resizer || !preview) return;
let startX = event.changedTouches ? event.changedTouches[0].pageX : event.clientX;
let startWidth = parseInt(document.defaultView.getComputedStyle(preview).width, 10);
event.preventDefault();
preview.classList.add('code-preview__preview--dragging');
document.documentElement.addEventListener('mousemove', dragMove);
document.documentElement.addEventListener('touchmove', dragMove);
document.documentElement.addEventListener('mouseup', dragStop);
document.documentElement.addEventListener('touchend', dragStop);
function dragMove(event) {
const width = startWidth + (event.changedTouches ? event.changedTouches[0].pageX : event.pageX) - startX;
preview.style.width = `${width}px`;
}
function dragStop() {
preview.classList.remove('code-preview__preview--dragging');
document.documentElement.removeEventListener('mousemove', dragMove);
document.documentElement.removeEventListener('touchmove', dragMove);
document.documentElement.removeEventListener('mouseup', dragStop);
document.documentElement.removeEventListener('touchend', dragStop);
}
}
//
// Toggle source mode
//
document.addEventListener('click', event => {
const button = event.target.closest('.code-preview__button');
const codeBlock = button?.closest('.code-preview');
if (button?.classList.contains('code-preview__button--html')) {
// Show HTML
setFlavor('html');
toggleSource(codeBlock, true);
} else if (button?.classList.contains('code-preview__button--react')) {
// Show React
setFlavor('react');
toggleSource(codeBlock, true);
} else if (button?.classList.contains('code-preview__toggle')) {
// Toggle source
toggleSource(codeBlock);
} else {
return;
}
// Update flavor buttons
[...document.querySelectorAll('.code-preview')].forEach(cb => {
cb.querySelector('.code-preview__button--html')?.classList.toggle(
'code-preview__button--selected',
flavor === 'html'
);
cb.querySelector('.code-preview__button--react')?.classList.toggle(
'code-preview__button--selected',
flavor === 'react'
);
});
});
function toggleSource(codeBlock, force) {
codeBlock.classList.toggle('code-preview--expanded', force);
event.target.setAttribute('aria-expanded', codeBlock.classList.contains('code-preview--expanded'));
}
//
// Open in CodePen
//
document.addEventListener('click', event => {
const button = event.target.closest('button');
if (button?.classList.contains('code-preview__button--codepen')) {
const codeBlock = button.closest('.code-preview');
const htmlExample = codeBlock.querySelector('.code-preview__source--html > pre > code')?.textContent;
const reactExample = codeBlock.querySelector('.code-preview__source--react > pre > code')?.textContent;
const isReact = flavor === 'react' && typeof reactExample === 'string';
const theme = document.documentElement.classList.contains('sl-theme-dark') ? 'dark' : 'light';
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
const isDark = theme === 'dark' || (theme === 'auto' && prefersDark);
const editors = isReact ? '0010' : '1000';
let htmlTemplate = '';
let jsTemplate = '';
let cssTemplate = '';
const form = document.createElement('form');
form.action = 'https://codepen.io/pen/define';
form.method = 'POST';
form.target = '_blank';
// HTML templates
if (!isReact) {
htmlTemplate =
`<script type="module" src="https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@${shoelaceVersion}/${cdndir}/shoelace.js"></script>\n` +
`\n${htmlExample}`;
jsTemplate = '';
}
// React templates
if (isReact) {
htmlTemplate = '<div id="root"></div>';
jsTemplate =
`import React from 'https://esm.sh/react@${reactVersion}';\n` +
`import ReactDOM from 'https://esm.sh/react-dom@${reactVersion}';\n` +
`import { setBasePath } from 'https://esm.sh/@shoelace-style/shoelace@${shoelaceVersion}/${cdndir}/utilities/base-path';\n` +
`\n` +
`// Set the base path for Shoelace assets\n` +
`setBasePath('https://esm.sh/@shoelace-style/shoelace@${shoelaceVersion}/${npmdir}/')\n` +
`\n${convertModuleLinks(reactExample)}\n` +
`\n` +
`ReactDOM.render(<App />, document.getElementById('root'));`;
}
// CSS templates
cssTemplate =
`@import 'https://cdn.jsdelivr.net/npm/@shoelace-style/shoelace@${shoelaceVersion}/${cdndir}/themes/${
isDark ? 'dark' : 'light'
}.css';\n` +
'\n' +
'body {\n' +
' font: 16px sans-serif;\n' +
' background-color: var(--sl-color-neutral-0);\n' +
' color: var(--sl-color-neutral-900);\n' +
' padding: 1rem;\n' +
'}';
// Docs: https://blog.codepen.io/documentation/prefill/
const data = {
title: '',
description: '',
tags: ['shoelace', 'web components'],
editors,
head: `<meta name="viewport" content="width=device-width">`,
html_classes: `sl-theme-${isDark ? 'dark' : 'light'}`,
css_external: ``,
js_external: ``,
js_module: true,
js_pre_processor: isReact ? 'babel' : 'none',
html: htmlTemplate,
css: cssTemplate,
js: jsTemplate
};
const input = document.createElement('input');
input.type = 'hidden';
input.name = 'data';
input.value = JSON.stringify(data);
form.append(input);
document.documentElement.append(form);
form.submit();
form.remove();
}
});
// Set the initial flavor
window.addEventListener('turbo:load', syncFlavor);
})();

272
docs/assets/scripts/docs.js Normal file
View File

@@ -0,0 +1,272 @@
//
// Sidebar
//
// When the sidebar is hidden, we apply the inert attribute to prevent focus from reaching it. Due to the many states
// the sidebar can have (e.g. static, hidden, expanded), we test for visibility by checking to see if it's placed
// offscreen or not. Then, on resize/transition we make sure to update the attribute accordingly.
//
(() => {
function getSidebar() {
return document.getElementById('sidebar');
}
function isSidebarOpen() {
return document.documentElement.classList.contains('sidebar-open');
}
function isSidebarVisible() {
return getSidebar().getBoundingClientRect().x >= 0;
}
function toggleSidebar(force) {
const isOpen = typeof force === 'boolean' ? force : !isSidebarOpen();
return document.documentElement.classList.toggle('sidebar-open', isOpen);
}
function updateInert() {
getSidebar().inert = !isSidebarVisible();
}
// Toggle the menu
document.addEventListener('click', event => {
const menuToggle = event.target.closest('#menu-toggle');
if (!menuToggle) return;
toggleSidebar();
});
// Update the sidebar's inert state when the window resizes and when the sidebar transitions
window.addEventListener('resize', () => toggleSidebar(false));
document.addEventListener('transitionend', event => {
const sidebar = event.target.closest('#sidebar');
if (!sidebar) return;
updateInert();
});
// Close when a menu item is selected on mobile
document.addEventListener('click', event => {
const sidebar = event.target.closest('#sidebar');
const link = event.target.closest('a');
if (!sidebar || !link) return;
if (isSidebarOpen()) {
toggleSidebar();
}
});
// Close when open and escape is pressed
document.addEventListener('keydown', event => {
if (event.key === 'Escape' && isSidebarOpen()) {
event.stopImmediatePropagation();
toggleSidebar();
}
});
// Close when clicking outside of the sidebar
document.addEventListener('mousedown', event => {
if (isSidebarOpen() & !event.target?.closest('#sidebar, #menu-toggle')) {
event.stopImmediatePropagation();
toggleSidebar();
}
});
updateInert();
})();
//
// Theme selector
//
(() => {
function getTheme() {
return localStorage.getItem('theme') || 'auto';
}
function isDark() {
if (theme === 'auto') {
return window.matchMedia('(prefers-color-scheme: dark)').matches;
}
return theme === 'dark';
}
function setTheme(newTheme) {
theme = newTheme;
localStorage.setItem('theme', theme);
// Update the UI
updateSelection();
// Toggle the dark mode class
document.documentElement.classList.toggle('sl-theme-dark', isDark());
}
function updateSelection() {
const menu = document.querySelector('#theme-selector sl-menu');
if (!menu) return;
[...menu.querySelectorAll('sl-menu-item')].map(item => (item.checked = item.getAttribute('value') === theme));
}
let theme = getTheme();
// Selection is not preserved when changing page, so update when opening dropdown
document.addEventListener('sl-show', event => {
const themeSelector = event.target.closest('#theme-selector');
if (!themeSelector) return;
updateSelection();
});
// Listen for selections
document.addEventListener('sl-select', event => {
const menu = event.target.closest('#theme-selector sl-menu');
if (!menu) return;
setTheme(event.detail.item.value);
});
// Update the theme when the preference changes
window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', () => setTheme(theme));
// Toggle with backslash
document.addEventListener('keydown', event => {
if (
event.key === '\\' &&
!event.composedPath().some(el => ['input', 'textarea'].includes(el?.tagName?.toLowerCase()))
) {
event.preventDefault();
setTheme(isDark() ? 'light' : 'dark');
}
});
// Set the initial theme and sync the UI
setTheme(theme);
})();
//
// Open details when printing
//
(() => {
const detailsOpenOnPrint = new Set();
window.addEventListener('beforeprint', () => {
detailsOpenOnPrint.clear();
document.querySelectorAll('details').forEach(details => {
if (details.open) {
detailsOpenOnPrint.add(details);
}
details.open = true;
});
});
window.addEventListener('afterprint', () => {
document.querySelectorAll('details').forEach(details => {
details.open = detailsOpenOnPrint.has(details);
});
detailsOpenOnPrint.clear();
});
})();
//
// Smooth links
//
(() => {
document.addEventListener('click', event => {
const link = event.target.closest('a');
const id = (link?.hash ?? '').substr(1);
const isFragment = link?.hasAttribute('href') && link?.getAttribute('href').startsWith('#');
if (!link || !isFragment || link.getAttribute('data-smooth-link') === 'false') {
return;
}
// Scroll to the top
if (link.hash === '') {
event.preventDefault();
window.scroll({ top: 0, behavior: 'smooth' });
history.pushState(undefined, undefined, location.pathname);
}
// Scroll to an id
if (id) {
const target = document.getElementById(id);
if (target) {
event.preventDefault();
window.scroll({ top: target.offsetTop, behavior: 'smooth' });
history.pushState(undefined, undefined, `#${id}`);
}
}
});
})();
//
// Table of Contents scrollspy
//
(() => {
// This will be stale if its not a function.
const getLinks = () => [...document.querySelectorAll('.content__toc a')];
const linkTargets = new WeakMap();
const visibleTargets = new WeakSet();
const observer = new IntersectionObserver(handleIntersect, { rootMargin: '0px 0px' });
let debounce;
function handleIntersect(entries) {
entries.forEach(entry => {
// Remember which targets are visible
if (entry.isIntersecting) {
visibleTargets.add(entry.target);
} else {
visibleTargets.delete(entry.target);
}
});
updateActiveLinks();
}
function updateActiveLinks() {
const links = getLinks();
// Find the first visible target and activate the respective link
links.find(link => {
const target = linkTargets.get(link);
if (target && visibleTargets.has(target)) {
links.forEach(el => el.classList.toggle('active', el === link));
return true;
}
return false;
});
}
// Observe link targets
function observeLinks() {
getLinks().forEach(link => {
const hash = link.hash.slice(1);
const target = hash ? document.querySelector(`.content__body #${hash}`) : null;
if (target) {
linkTargets.set(link, target);
observer.observe(target);
}
});
}
observeLinks();
document.addEventListener('turbo:load', updateActiveLinks);
document.addEventListener('turbo:load', observeLinks);
})();
//
// Show custom versions in the sidebar
//
(() => {
function updateVersion() {
const el = document.querySelector('.sidebar-version');
if (!el) return;
if (location.hostname === 'next.shoelace.style') el.textContent = 'Next';
if (location.hostname === 'localhost') el.textContent = 'Development';
}
updateVersion();
document.addEventListener('turbo:load', updateVersion);
})();

View File

@@ -0,0 +1,376 @@
(() => {
// Append the search dialog to the body
const siteSearch = document.createElement('div');
const scrollbarWidth = Math.abs(window.innerWidth - document.documentElement.clientWidth);
siteSearch.classList.add('search');
siteSearch.innerHTML = `
<div class="search__overlay"></div>
<dialog id="search-dialog" class="search__dialog">
<div class="search__content">
<div class="search__header">
<div id="search-combobox" class="search__input-wrapper">
<sl-icon name="search"></sl-icon>
<input
id="search-input"
class="search__input"
type="search"
placeholder="Search"
autocomplete="off"
autocorrect="off"
autocapitalize="off"
enterkeyhint="go"
spellcheck="false"
maxlength="100"
role="combobox"
aria-autocomplete="list"
aria-expanded="true"
aria-controls="search-listbox"
aria-haspopup="listbox"
aria-activedescendant
>
<button type="button" class="search__clear-button" aria-label="Clear entry" tabindex="-1" hidden>
<sl-icon name="x-circle-fill"></sl-icon>
</button>
</div>
</div>
<div class="search__body">
<ul
id="search-listbox"
class="search__results"
role="listbox"
aria-label="Search results"
></ul>
<div class="search__empty">No matching pages</div>
</div>
<footer class="search__footer">
<small><kbd>↑</kbd> <kbd>↓</kbd> Navigate</small>
<small><kbd>↲</kbd> Select</small>
<small><kbd>Esc</kbd> Close</small>
</footer>
</div>
</dialog>
`;
const overlay = siteSearch.querySelector('.search__overlay');
const dialog = siteSearch.querySelector('.search__dialog');
const input = siteSearch.querySelector('.search__input');
const clearButton = siteSearch.querySelector('.search__clear-button');
const results = siteSearch.querySelector('.search__results');
const version = document.documentElement.getAttribute('data-shoelace-version');
const key = `search_${version}`;
const searchDebounce = 50;
const animationDuration = 150;
let isShowing = false;
let searchTimeout;
let searchIndex;
let map;
const loadSearchIndex = new Promise(resolve => {
const cache = localStorage.getItem(key);
const wait = 'requestIdleCallback' in window ? requestIdleCallback : requestAnimationFrame;
// Cleanup older search indices (everything before this version)
try {
const items = { ...localStorage };
Object.keys(items).forEach(k => {
if (key > k) {
localStorage.removeItem(k);
}
});
} catch {
/* do nothing */
}
// Look for a cached index
try {
if (cache) {
const data = JSON.parse(cache);
searchIndex = window.lunr.Index.load(data.searchIndex);
map = data.map;
return resolve();
}
} catch {
/* do nothing */
}
// Wait until idle to fetch the index
wait(() => {
fetch('/assets/search.json')
.then(res => res.json())
.then(data => {
if (!window.lunr) {
console.error('The Lunr search client has not yet been loaded.');
}
searchIndex = window.lunr.Index.load(data.searchIndex);
map = data.map;
// Cache the search index for this version
if (version) {
try {
localStorage.setItem(key, JSON.stringify(data));
} catch (err) {
console.warn(`Unable to cache the search index: ${err}`);
}
}
resolve();
});
});
});
async function show() {
isShowing = true;
document.body.append(siteSearch);
document.body.classList.add('search-visible');
document.body.style.setProperty('--docs-search-scroll-lock-size', `${scrollbarWidth}px`);
clearButton.hidden = true;
requestAnimationFrame(() => input.focus());
updateResults();
dialog.showModal();
await Promise.all([
dialog.animate(
[
{ opacity: 0, transform: 'scale(.9)', transformOrigin: 'top' },
{ opacity: 1, transform: 'scale(1)', transformOrigin: 'top' }
],
{ duration: animationDuration }
).finished,
overlay.animate([{ opacity: 0 }, { opacity: 1 }], { duration: animationDuration }).finished
]);
dialog.addEventListener('mousedown', handleMouseDown);
dialog.addEventListener('keydown', handleKeyDown);
}
async function hide() {
isShowing = false;
await Promise.all([
dialog.animate(
[
{ opacity: 1, transform: 'scale(1)', transformOrigin: 'top' },
{ opacity: 0, transform: 'scale(.9)', transformOrigin: 'top' }
],
{ duration: animationDuration }
).finished,
overlay.animate([{ opacity: 1 }, { opacity: 0 }], { duration: animationDuration }).finished
]);
dialog.close();
input.blur(); // otherwise Safari will scroll to the bottom of the page on close
input.value = '';
document.body.classList.remove('search-visible');
document.body.style.removeProperty('--docs-search-scroll-lock-size');
siteSearch.remove();
updateResults();
dialog.removeEventListener('mousedown', handleMouseDown);
dialog.removeEventListener('keydown', handleKeyDown);
}
function handleInput() {
clearButton.hidden = input.value === '';
// Debounce search queries
clearTimeout(searchTimeout);
searchTimeout = setTimeout(() => updateResults(input.value), searchDebounce);
}
function handleClear() {
clearButton.hidden = true;
input.value = '';
input.focus();
updateResults();
}
function handleMouseDown(event) {
if (!event.target.closest('.search__content')) {
hide();
}
}
function handleKeyDown(event) {
// Close when pressing escape
if (event.key === 'Escape') {
event.preventDefault(); // prevent <dialog> from closing immediately so it can animate
event.stopImmediatePropagation();
hide();
return;
}
// Handle keyboard selections
if (['ArrowDown', 'ArrowUp', 'Home', 'End', 'Enter'].includes(event.key)) {
event.preventDefault();
const currentEl = results.querySelector('[data-selected="true"]');
const items = [...results.querySelectorAll('li')];
const index = items.indexOf(currentEl);
let nextEl;
if (items.length === 0) {
return;
}
switch (event.key) {
case 'ArrowUp':
nextEl = items[Math.max(0, index - 1)];
break;
case 'ArrowDown':
nextEl = items[Math.min(items.length - 1, index + 1)];
break;
case 'Home':
nextEl = items[0];
break;
case 'End':
nextEl = items[items.length - 1];
break;
case 'Enter':
currentEl?.querySelector('a')?.click();
break;
}
// Update the selected item
items.forEach(item => {
if (item === nextEl) {
input.setAttribute('aria-activedescendant', item.id);
item.setAttribute('data-selected', 'true');
nextEl.scrollIntoView({ block: 'nearest' });
} else {
item.setAttribute('data-selected', 'false');
}
});
}
}
async function updateResults(query = '') {
try {
await loadSearchIndex;
const hasQuery = query.length > 0;
const searchTerms = query
.split(' ')
.map((term, index, arr) => {
// Search API: https://lunrjs.com/guides/searching.html
if (index === arr.length - 1) {
// The last term is not mandatory and 1x fuzzy. We also duplicate it with a wildcard to match partial words
// as the user types.
return `${term}~1 ${term}*`;
} else {
// All other terms are mandatory and 1x fuzzy
return `+${term}~1`;
}
})
.join(' ');
const matches = hasQuery ? searchIndex.search(searchTerms) : [];
const hasResults = hasQuery && matches.length > 0;
siteSearch.classList.toggle('search--has-results', hasQuery && hasResults);
siteSearch.classList.toggle('search--no-results', hasQuery && !hasResults);
input.setAttribute('aria-activedescendant', '');
results.innerHTML = '';
matches.forEach((match, index) => {
const page = map[match.ref];
const li = document.createElement('li');
const a = document.createElement('a');
const displayTitle = page.title ?? '';
const displayDescription = page.description ?? '';
const displayUrl = page.url.replace(/^\//, '').replace(/\/$/, '');
let icon = 'file-text';
a.setAttribute('role', 'option');
a.setAttribute('id', `search-result-item-${match.ref}`);
if (page.url.includes('getting-started/')) {
icon = 'lightbulb';
}
if (page.url.includes('resources/')) {
icon = 'book';
}
if (page.url.includes('components/')) {
icon = 'puzzle';
}
if (page.url.includes('tokens/')) {
icon = 'palette2';
}
if (page.url.includes('utilities/')) {
icon = 'wrench';
}
if (page.url.includes('tutorials/')) {
icon = 'joystick';
}
li.classList.add('search__result');
li.setAttribute('role', 'option');
li.setAttribute('id', `search-result-item-${match.ref}`);
li.setAttribute('data-selected', index === 0 ? 'true' : 'false');
a.href = page.url;
a.innerHTML = `
<div class="search__result-icon" aria-hidden="true">
<sl-icon name="${icon}"></sl-icon>
</div>
<div class="search__result__details">
<div class="search__result-title"></div>
<div class="search__result-description"></div>
<div class="search__result-url"></div>
</div>
`;
a.querySelector('.search__result-title').textContent = displayTitle;
a.querySelector('.search__result-description').textContent = displayDescription;
a.querySelector('.search__result-url').textContent = displayUrl;
li.appendChild(a);
results.appendChild(li);
});
} catch {
// Ignore query errors as the user types
}
}
// Show the search dialog when clicking on data-plugin="search"
document.addEventListener('click', event => {
const searchButton = event.target.closest('[data-plugin="search"]');
if (searchButton) {
show();
}
});
// Show the search dialog when slash (or CMD+K) is pressed and focus is not inside a form element
document.addEventListener('keydown', event => {
if (
!isShowing &&
(event.key === '/' || (event.key === 'k' && (event.metaKey || event.ctrlKey))) &&
!event.composedPath().some(el => ['input', 'textarea'].includes(el?.tagName?.toLowerCase()))
) {
event.preventDefault();
show();
}
});
// Purge cache when we press CMD+CTRL+R
document.addEventListener('keydown', event => {
if ((event.metaKey || event.ctrlKey) && event.shiftKey && event.key === 'r') {
localStorage.clear();
}
});
input.addEventListener('input', handleInput);
clearButton.addEventListener('click', handleClear);
// Close when a result is selected
results.addEventListener('click', event => {
if (event.target.closest('a')) {
hide();
}
});
})();

View File

@@ -0,0 +1,29 @@
import * as Turbo from 'https://cdn.jsdelivr.net/npm/@hotwired/turbo@7.3.0/+esm';
(() => {
if (!window.scrollPositions) {
window.scrollPositions = {};
}
function preserveScroll() {
document.querySelectorAll('[data-preserve-scroll').forEach(element => {
scrollPositions[element.id] = element.scrollTop;
});
}
function restoreScroll(event) {
document.querySelectorAll('[data-preserve-scroll').forEach(element => {
element.scrollTop = scrollPositions[element.id];
});
if (event.detail && event.detail.newBody) {
event.detail.newBody.querySelectorAll('[data-preserve-scroll').forEach(element => {
element.scrollTop = scrollPositions[element.id];
});
}
}
window.addEventListener('turbo:before-cache', preserveScroll);
window.addEventListener('turbo:before-render', restoreScroll);
window.addEventListener('turbo:render', restoreScroll);
})();

View File

@@ -0,0 +1,173 @@
/* Interactive code blocks */
.code-preview {
position: relative;
border-radius: 3px;
background-color: var(--sl-color-neutral-50);
margin-bottom: 1.5rem;
}
.code-preview__preview {
position: relative;
border: solid 1px var(--sl-color-neutral-200);
border-bottom: none;
border-top-left-radius: 3px;
border-top-right-radius: 3px;
background-color: var(--sl-color-neutral-0);
min-width: 20rem;
max-width: 100%;
padding: 1.5rem 3.25rem 1.5rem 1.5rem;
}
/* Block the preview while dragging to prevent iframes from intercepting drag events */
.code-preview__preview--dragging:after {
content: '';
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
opacity: 0;
cursor: ew-resize;
}
.code-preview__resizer {
display: flex;
align-items: center;
justify-content: center;
position: absolute;
top: 0;
right: 0;
bottom: 0;
width: 1.75rem;
font-size: 20px;
color: var(--sl-color-neutral-600);
background-color: var(--sl-color-neutral-0);
border-left: solid 1px var(--sl-color-neutral-200);
border-top-right-radius: 3px;
cursor: ew-resize;
}
@media screen and (max-width: 600px) {
.code-preview__preview {
padding-right: 1.5rem;
}
.code-preview__resizer {
display: none;
}
}
.code-preview__source {
border: solid 1px var(--sl-color-neutral-200);
border-bottom: none;
border-radius: 0 !important;
display: none;
}
.code-preview--expanded .code-preview__source {
display: block;
}
.code-preview__source pre {
margin: 0;
}
.code-preview__buttons {
position: relative;
border: solid 1px var(--sl-color-neutral-200);
border-bottom-left-radius: 3px;
border-bottom-right-radius: 3px;
display: flex;
}
.code-preview__button {
flex: 0 0 auto;
height: 2.5rem;
min-width: 2.5rem;
border: none;
border-radius: 0;
background: var(--sl-color-neutral-0);
font: inherit;
font-size: 0.7rem;
font-weight: 500;
text-transform: uppercase;
color: var(--sl-color-neutral-600);
padding: 0 1rem;
cursor: pointer;
}
.code-preview__button:not(:last-of-type) {
border-right: solid 1px var(--sl-color-neutral-200);
}
.code-preview__button--html,
.code-preview__button--react {
width: 70px;
display: flex;
place-items: center;
justify-content: center;
}
.code-preview__button--selected {
font-weight: 700;
color: var(--sl-color-primary-600);
}
.code-preview__button--codepen {
display: flex;
place-items: center;
width: 6rem;
}
.code-preview__button:first-of-type {
border-bottom-left-radius: 3px;
}
.code-preview__button:last-of-type {
border-bottom-right-radius: 3px;
}
.code-preview__button:hover,
.code-preview__button:active {
box-shadow: 0 0 0 1px var(--sl-color-primary-400);
border-right-color: transparent;
background-color: var(--sl-color-primary-50);
color: var(--sl-color-primary-600);
z-index: 1;
}
.code-preview__button:focus-visible {
outline: none;
outline: var(--sl-focus-ring);
z-index: 2;
}
.code-preview__toggle {
position: relative;
display: flex;
flex: 1 1 auto;
align-items: center;
justify-content: center;
width: 100%;
color: var(--sl-color-neutral-600);
cursor: pointer;
}
.code-preview__toggle svg {
width: 1em;
height: 1em;
margin-left: 0.25rem;
}
.code-preview--expanded .code-preview__toggle svg {
transform: rotate(180deg);
}
/* We can apply data-flavor="html|react" to any element on the page to toggle it when the flavor changes */
.flavor-html [data-flavor]:not([data-flavor='html']) {
display: none;
}
.flavor-react [data-flavor]:not([data-flavor='react']) {
display: none;
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,347 @@
/* Search plugin */
:root,
:root.sl-theme-dark {
--docs-search-box-background: var(--sl-color-neutral-0);
--docs-search-box-border-width: 1px;
--docs-search-box-border-color: var(--sl-color-neutral-300);
--docs-search-box-color: var(--sl-color-neutral-600);
--docs-search-dialog-background: var(--sl-color-neutral-0);
--docs-search-border-width: var(--docs-border-width);
--docs-search-border-color: var(--docs-border-color);
--docs-search-text-color: var(--sl-color-neutral-900);
--docs-search-text-color-muted: var(--sl-color-neutral-500);
--docs-search-font-weight-normal: var(--sl-font-weight-normal);
--docs-search-font-weight-semibold: var(--sl-font-weight-semibold);
--docs-search-border-radius: calc(2 * var(--docs-border-radius));
--docs-search-accent-color: var(--sl-color-primary-600);
--docs-search-icon-color: var(--sl-color-neutral-500);
--docs-search-icon-color-active: var(--sl-color-neutral-600);
--docs-search-shadow: var(--docs-shadow-x-large);
--docs-search-result-background-hover: var(--sl-color-neutral-100);
--docs-search-result-color-hover: var(--sl-color-neutral-900);
--docs-search-result-background-active: var(--sl-color-primary-600);
--docs-search-result-color-active: var(--sl-color-neutral-0);
--docs-search-focus-ring: var(--sl-focus-ring);
--docs-search-overlay-background: rgb(0 0 0 / 0.33);
}
:root.sl-theme-dark {
--docs-search-overlay-background: rgb(71 71 71 / 0.33);
}
body.search-visible {
padding-right: var(--docs-search-scroll-lock-size) !important;
overflow: hidden !important;
}
/* Search box */
.search-box {
flex: 1 1 auto;
display: flex;
align-items: center;
width: 100%;
border: none;
border-radius: 9999px;
background: var(--docs-search-box-background);
border: solid var(--docs-search-box-border-width) var(--docs-search-box-border-color);
font: inherit;
color: var(--docs-search-box-color);
padding: 0.75rem 1rem;
margin: var(--sl-spacing-large) 0;
cursor: pointer;
}
.search-box span {
flex: 1 1 auto;
width: 1rem;
height: 1rem;
text-align: left;
line-height: 1;
margin: 0 0.75rem;
}
.search-box:focus {
outline: none;
}
.search-box:focus-visible {
outline: var(--docs-search-focus-ring);
}
/* Site search */
.search {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
z-index: 9999;
}
.search[hidden] {
display: none;
}
.search__overlay {
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: var(--docs-search-overlay-background);
z-index: -1;
}
.search__dialog {
width: 100%;
height: 100%;
max-width: none;
max-height: none;
background: transparent;
border: none;
padding: 0;
margin: 0;
}
.search__dialog:focus {
outline: none;
}
.search__dialog::backdrop {
display: none;
}
/* Fixes an iOS Safari 16.4 bug that draws the parent element's border radius incorrectly when showing/hiding results */
.search__header {
background-color: var(--docs-search-dialog-background);
border-radius: var(--docs-search-border-radius);
}
.search--has-results .search__header {
border-top-left-radius: var(--docs-search-border-radius);
border-top-right-radius: var(--docs-search-border-radius);
border-bottom-left-radius: 0;
border-bottom-right-radius: 0;
}
.search__content {
display: flex;
flex-direction: column;
width: 100%;
max-width: 500px;
max-height: calc(100vh - 20rem);
background-color: var(--docs-search-dialog-background);
border-radius: var(--docs-search-border-radius);
box-shadow: var(--docs-search-shadow);
padding: 0;
margin: 10rem auto;
}
@media screen and (max-width: 900px) {
.search__content {
max-width: calc(100% - 2rem);
max-height: calc(90svh);
margin: 4vh 1rem;
}
}
.search__input-wrapper {
display: flex;
align-items: center;
}
.search__input-wrapper sl-icon {
width: 1.5rem;
height: 1.5rem;
flex: 0 0 auto;
color: var(--docs-search-icon-color);
margin: 0 1.5rem;
}
.search__clear-button {
display: flex;
background: none;
border: none;
font: inherit;
padding: 0;
margin: 0;
cursor: pointer;
}
.search__clear-button[hidden] {
display: none;
}
.search__clear-button:active sl-icon {
color: var(--docs-search-icon-color-active);
}
.search__input {
flex: 1 1 auto;
min-width: 0;
border: none;
font: inherit;
font-size: 1.5rem;
font-weight: var(--docs-search-font-weight-normal);
color: var(--docs-search-text-color);
background: transparent;
padding: 1rem 0;
margin: 0;
}
.search__input::placeholder {
color: var(--docs-search-text-color-muted);
}
.search__input::-webkit-search-decoration,
.search__input::-webkit-search-cancel-button,
.search__input::-webkit-search-results-button,
.search__input::-webkit-search-results-decoration {
display: none;
}
.search__input:focus,
.search__input:focus-visible {
outline: none;
}
.search__body {
flex: 1 1 auto;
overflow: auto;
}
.search--has-results .search__body {
border-top: solid var(--docs-search-border-width) var(--docs-search-border-color);
}
.search__results {
display: none;
line-height: 1.2;
list-style: none;
padding: 0.5rem 0;
margin: 0;
}
.search--has-results .search__results {
display: block;
}
.search__results a {
display: block;
text-decoration: none;
padding: 0.5rem 1.5rem;
}
.search__results a:focus-visible {
outline: var(--docs-search-focus-ring);
}
.search__results li a:hover,
.search__results li a:hover small {
background-color: var(--docs-search-result-background-hover);
color: var(--docs-search-result-color-hover);
}
.search__results li[data-selected='true'] a,
.search__results li[data-selected='true'] a * {
outline: none;
background-color: var(--docs-search-result-background-active);
color: var(--docs-search-result-color-active);
}
.search__results h3 {
font-weight: var(--docs-search-font-weight-semibold);
margin: 0;
}
.search__results small {
display: block;
color: var(--docs-search-text-color-muted);
}
.search__result {
padding: 0;
margin: 0;
}
.search__result a {
display: flex;
align-items: center;
gap: 1rem;
}
.search__result-icon {
flex: 0 0 auto;
display: flex;
color: var(--docs-search-text-color-muted);
}
.search__result-icon sl-icon {
font-size: 1.5rem;
}
.search__result__details {
width: calc(100% - 3rem);
}
.search__result-title,
.search__result-description,
.search__result-url {
max-width: 400px;
line-height: 1.3;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.search__result-title {
font-size: 1.2rem;
font-weight: var(--docs-search-font-weight-semibold);
color: var(--docs-search-accent-color);
}
.search__result-description {
font-size: 0.875rem;
color: var(--docs-search-text-color);
}
.search__result-url {
font-size: 0.875rem;
color: var(--docs-search-text-color-muted);
}
.search__empty {
display: none;
border-top: solid var(--docs-search-border-width) var(--docs-search-border-color);
text-align: center;
color: var(--docs-search-text-color-muted);
padding: 2rem;
}
.search--no-results .search__empty {
display: block;
}
.search__footer {
display: flex;
justify-content: center;
gap: 2rem;
border-top: solid var(--docs-search-border-width) var(--docs-search-border-color);
border-bottom-left-radius: inherit;
border-bottom-right-radius: inherit;
padding: 1rem;
}
.search__footer small {
color: var(--docs-search-text-color-muted);
}
.search__footer small kbd:last-of-type {
margin-right: 0.25rem;
}
@media screen and (max-width: 900px) {
.search__footer {
display: none;
}
}

View File

@@ -1,234 +0,0 @@
# Alert
[component-header:sl-alert]
Alerts are used to display important messages either inline or as toast notifications.
```html preview
<sl-alert open>
<sl-icon slot="icon" name="info-circle"></sl-icon>
This is a standard alert. You can customize its content and even the icon.
</sl-alert>
```
?> Alerts will not be visible if the `open` attribute is not present.
## Examples
### Types
Set the `type` attribute to change the alert's type.
```html preview
<sl-alert type="primary" open>
<sl-icon slot="icon" name="info-circle"></sl-icon>
<strong>This is super informative</strong><br>
You can tell by how pretty the alert is.
</sl-alert>
<br>
<sl-alert type="success" open>
<sl-icon slot="icon" name="check2-circle"></sl-icon>
<strong>Your changes have been saved</strong><br>
You can safely exit the app now.
</sl-alert>
<br>
<sl-alert type="neutral" open>
<sl-icon slot="icon" name="gear"></sl-icon>
<strong>Your settings have been updated</strong><br>
Settings will take affect on next login.
</sl-alert>
<br>
<sl-alert type="warning" open>
<sl-icon slot="icon" name="exclamation-triangle"></sl-icon>
<strong>Your session has ended</strong><br>
Please login again to continue.
</sl-alert>
<br>
<sl-alert type="danger" open>
<sl-icon slot="icon" name="exclamation-octagon"></sl-icon>
<strong>Your account has been deleted</strong><br>
We're very sorry to see you go!
</sl-alert>
```
### Closable
Add the `closable` attribute to show a close button that will hide the alert.
```html preview
<sl-alert type="primary" open closable class="alert-closable">
<sl-icon slot="icon" name="info-circle"></sl-icon>
You can close this alert any time!
</sl-alert>
<script>
const alert = document.querySelector('.alert-closable');
alert.addEventListener('sl-after-hide', () => {
setTimeout(() => alert.open = true, 2000);
});
</script>
```
### Without Icons
Icons are optional. Simply omit the `icon` slot if you don't want them.
```html preview
<sl-alert type="primary" open>
Nothing fancy here, just a simple alert.
</sl-alert>
```
### Duration
Set the `duration` attribute to automatically hide an alert after a period of time. This is useful for alerts that don't require acknowledgement.
```html preview
<div class="alert-duration">
<sl-button type="primary">Show Alert</sl-button>
<sl-alert type="primary" duration="3000" closable>
<sl-icon slot="icon" name="info-circle"></sl-icon>
This alert will automatically hide itself after three seconds, unless you interact with it.
</sl-alert>
</div>
<script>
const container = document.querySelector('.alert-duration');
const button = container.querySelector('sl-button');
const alert = container.querySelector('sl-alert');
button.addEventListener('click', () => alert.show());
</script>
<style>
.alert-duration sl-alert {
margin-top: var(--sl-spacing-medium);
}
</style>
```
### Toast Notifications
To display an alert as a toast notification, or "toast", create the alert and call its `toast()` method. This will move the alert out of its position in the DOM and into [the toast stack](#the-toast-stack) where it will be shown. Once dismissed, it will be removed from the DOM completely. To reuse a toast, store a reference to it and call `toast()` again later on.
You should always use the `closable` attribute so users can dismiss the notification. It's also common to set a reasonable `duration` when the notification doesn't require acknowledgement.
```html preview
<div class="alert-toast">
<sl-button type="primary">Primary</sl-button>
<sl-button type="success">Success</sl-button>
<sl-button type="neutral">Neutral</sl-button>
<sl-button type="warning">Warning</sl-button>
<sl-button type="danger">Danger</sl-button>
<sl-alert type="primary" duration="3000" closable>
<sl-icon slot="icon" name="info-circle"></sl-icon>
<strong>This is super informative</strong><br>
You can tell by how pretty the alert is.
</sl-alert>
<sl-alert type="success" duration="3000" closable>
<sl-icon slot="icon" name="check2-circle"></sl-icon>
<strong>Your changes have been saved</strong><br>
You can safely exit the app now.
</sl-alert>
<sl-alert type="neutral" duration="3000" closable>
<sl-icon slot="icon" name="gear"></sl-icon>
<strong>Your settings have been updated</strong><br>
Settings will take affect on next login.
</sl-alert>
<sl-alert type="warning" duration="3000" closable>
<sl-icon slot="icon" name="exclamation-triangle"></sl-icon>
<strong>Your session has ended</strong><br>
Please login again to continue.
</sl-alert>
<sl-alert type="danger" duration="3000" closable>
<sl-icon slot="icon" name="exclamation-octagon"></sl-icon>
<strong>Your account has been deleted</strong><br>
We're very sorry to see you go!
</sl-alert>
</div>
<script>
const container = document.querySelector('.alert-toast');
['primary', 'success', 'neutral', 'warning', 'danger'].map(type => {
const button = container.querySelector(`sl-button[type="${type}"]`);
const alert = container.querySelector(`sl-alert[type="${type}"]`);
button.addEventListener('click', () => alert.toast());
});
</script>
```
### Creating Toasts Imperatively
For convenience, you can create a utility that emits toast notifications with a function call rather than composing them in your HTML. To do this, generate the alert with JavaScript, append it to the body, and call the `toast()` method as shown in the example below.
```html preview
<div class="alert-toast-wrapper">
<sl-button type="primary">Create Toast</sl-button>
</div>
<script>
const container = document.querySelector('.alert-toast-wrapper');
const button = container.querySelector('sl-button');
let count = 0;
// Always escape HTML for text arguments!
function escapeHtml(html) {
const div = document.createElement('div');
div.textContent = html;
return div.innerHTML;
}
// Custom function to emit toast notifications
function notify(message, type = 'primary', icon = 'info-circle', duration = 3000) {
const alert = Object.assign(document.createElement('sl-alert'), {
type: type,
closable: true,
duration: duration,
innerHTML: `
<sl-icon name="${icon}" slot="icon"></sl-icon>
${escapeHtml(message)}
`
});
document.body.append(alert);
return alert.toast();
}
button.addEventListener('click', () => {
notify(`This is custom toast #${++count}`);
});
</script>
```
### The Toast Stack
The toast stack is a fixed position singleton element created and managed internally by the alert component. It will be added and removed from the DOM as needed when toasts are shown. When more than one toast is visible, they will stack vertically in the toast stack.
By default, the toast stack is positioned at the top-right of the viewport. You can change its position by targeting `.sl-toast-stack` in your stylesheet. To make toasts appear at the top-left of the viewport, for example, use the following styles.
```css
.sl-toast-stack {
left: 0;
right: auto;
}
```
?> By design, it is not possible to show toasts in more than one stack simultaneously. Such behavior is confusing and makes for a poor user experience.
[component-metadata:sl-alert]

View File

@@ -1,63 +0,0 @@
# Animated Image
[component-header:sl-animated-image]
A component for displaying animated GIFs and WEBPs that play and pause on interaction.
```html preview
<sl-animated-image
src="/assets/images/walk.gif"
alt="Animation of untied shoes walking on pavement"
></sl-animated-image>
```
## Examples
### WEBP Images
Both GIF and WEBP images are supported.
```html preview
<sl-animated-image
src="/assets/images/tie.webp"
alt="Animation of a shoe being tied"
></sl-animated-image>
```
### Setting a Width and Height
To set a custom size, apply a width and/or height to the host element.
```html preview
<sl-animated-image
src="/assets/images/walk.gif"
alt="Animation of untied shoes walking on pavement"
style="width: 150px; height: 200px;"
>
</sl-animated-image>
```
### Customizing the Control Box
You can change the appearance and location of the control box by targeting the `control-box` part in your styles.
```html preview
<sl-animated-image
src="/assets/images/walk.gif"
alt="Animation of untied shoes walking on pavement"
class="animated-image-custom-control-box"
></sl-animated-image>
<style>
.animated-image-custom-control-box::part(control-box) {
top: auto;
right: auto;
bottom: 1rem;
left: 1rem;
background-color: deeppink;
color: white;
}
</style>
```
[component-metadata:sl-animated-image]

View File

@@ -1,86 +0,0 @@
# Avatar
[component-header:sl-avatar]
Avatars are used to represent a person or object.
```html preview
<sl-avatar></sl-avatar>
```
## Examples
### Images
To use an image for the avatar, set the `image` and `alt` attributes. This will take priority and be shown over initials and icons.
```html preview
<sl-avatar
image="https://images.unsplash.com/photo-1529778873920-4da4926a72c2?ixlib=rb-1.2.1&auto=format&fit=crop&w=300&q=80"
alt="Gray tabby kitten looking down"
></sl-avatar>
```
### Initials
When you don't have an image to use, you can set the `initials` attribute to show something more personalized than an icon.
```html preview
<sl-avatar initials="SL"></sl-avatar>
```
### Custom Icons
When no image or initials are set, an icon will be shown. The default avatar shows a generic "user" icon, but you can customize this with the `icon` slot.
```html preview
<sl-avatar>
<sl-icon slot="icon" name="image"></sl-icon>
</sl-avatar>
<sl-avatar>
<sl-icon slot="icon" name="archive"></sl-icon>
</sl-avatar>
<sl-avatar>
<sl-icon slot="icon" name="briefcase"></sl-icon>
</sl-avatar>
```
### Shapes
Avatars can be shaped using the `shape` attribute.
```html preview
<sl-avatar shape="square"></sl-avatar>
<sl-avatar shape="rounded"></sl-avatar>
<sl-avatar shape="circle"></sl-avatar>
```
### Avatar Groups
You can group avatars with a few lines of CSS.
```html preview
<div class="avatar-group">
<sl-avatar image="https://images.unsplash.com/photo-1490150028299-bf57d78394e0?ixid=MXwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHw%3D&ixlib=rb-1.2.1&auto=format&fit=crop&w=256&h=256&q=80&crop=right"></sl-avatar>
<sl-avatar image="https://images.unsplash.com/photo-1503454537195-1dcabb73ffb9?ixid=MXwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHw%3D&ixlib=rb-1.2.1&auto=format&fit=crop&w=256&h=256&crop=left&q=80"></sl-avatar>
<sl-avatar image="https://images.unsplash.com/photo-1456439663599-95b042d50252?ixid=MXwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHw%3D&ixlib=rb-1.2.1&auto=format&fit=crop&w=256&h=256&crop=left&q=80"></sl-avatar>
<sl-avatar image="https://images.unsplash.com/flagged/photo-1554078875-e37cb8b0e27d?ixid=MXwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHw%3D&ixlib=rb-1.2.1&auto=format&fit=crop&w=256&h=256&crop=top&q=80"></sl-avatar>
</div>
<style>
.avatar-group sl-avatar:not(:first-of-type) {
margin-left: -1rem;
}
.avatar-group sl-avatar::part(base) {
border: solid 2px rgb(var(--sl-color-neutral-0));
}
</style>
```
[component-metadata:sl-avatar]

View File

@@ -1,90 +0,0 @@
# Badge
[component-header:sl-badge]
Badges are used to draw attention and display statuses or counts.
```html preview
<sl-badge>Badge</sl-badge>
```
## Examples
### Types
Set the `type` attribute to change the badge's type.
```html preview
<sl-badge type="primary">Primary</sl-badge>
<sl-badge type="success">Success</sl-badge>
<sl-badge type="neutral">Neutral</sl-badge>
<sl-badge type="warning">Warning</sl-badge>
<sl-badge type="danger">Danger</sl-badge>
```
### Pill Badges
Use the `pill` attribute to give badges rounded edges.
```html preview
<sl-badge type="primary" pill>Primary</sl-badge>
<sl-badge type="success" pill>Success</sl-badge>
<sl-badge type="neutral" pill>Neutral</sl-badge>
<sl-badge type="warning" pill>Warning</sl-badge>
<sl-badge type="danger" pill>Danger</sl-badge>
```
### Pulsating Badges
Use the `pulse` attribute to draw attention to the badge with a subtle animation.
```html preview
<div class="badge-pulse">
<sl-badge type="primary" pill pulse>1</sl-badge>
<sl-badge type="success" pill pulse>1</sl-badge>
<sl-badge type="neutral" pill pulse>1</sl-badge>
<sl-badge type="warning" pill pulse>1</sl-badge>
<sl-badge type="danger" pill pulse>1</sl-badge>
</div>
<style>
.badge-pulse sl-badge:not(:last-of-type) {
margin-right: 1rem;
}
</style>
```
### With Buttons
One of the most common use cases for badges is attaching them to buttons. To make this easier, badges will be automatically positioned at the top-right when they're a child of a button.
```html preview
<sl-button>
Requests
<sl-badge pill>30</sl-badge>
</sl-button>
<sl-button style="margin-left: 1rem;">
Warnings
<sl-badge type="warning" pill>8</sl-badge>
</sl-button>
<sl-button style="margin-left: 1rem;">
Errors
<sl-badge type="danger" pill>6</sl-badge>
</sl-button>
```
### With Menu Items
When including badges in menu items, use the `suffix` slot to make sure they're aligned correctly.
```html preview
<sl-menu style="max-width: 240px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-label>Messages</sl-menu-label>
<sl-menu-item>Comments <sl-badge slot="suffix" type="neutral" pill>4</sl-badge></sl-menu-item>
<sl-menu-item>Replies <sl-badge slot="suffix" type="neutral" pill>12</sl-badge></sl-menu-item>
</sl-menu>
```
[component-metadata:sl-badge]

View File

@@ -1,20 +0,0 @@
# Breadcrumb Item
[component-header:sl-breadcrumb-item]
Breadcrumb Items are used inside [breadcrumbs](/components/breadcrumb) to represent different links.
```html preview
<sl-breadcrumb>
<sl-breadcrumb-item>
<sl-icon slot="prefix" name="house"></sl-icon>
Home
</sl-breadcrumb-item>
<sl-breadcrumb-item>Clothing</sl-breadcrumb-item>
<sl-breadcrumb-item>Shirts</sl-breadcrumb-item>
</sl-breadcrumb>
```
?> Additional demonstrations can be found in the [breadcrumb examples](/components/breadcrumb).
[component-metadata:sl-breadcrumb-item]

View File

@@ -1,132 +0,0 @@
# Breadcrumb
[component-header:sl-breadcrumb]
Breadcrumbs provide a group of links so users can easily navigate a website's hierarchy.
Breadcrumbs are usually placed before a page's main content with the current page shown last to indicate the user's position in the navigation.
```html preview
<sl-breadcrumb>
<sl-breadcrumb-item>Catalog</sl-breadcrumb-item>
<sl-breadcrumb-item>Clothing</sl-breadcrumb-item>
<sl-breadcrumb-item>Women's</sl-breadcrumb-item>
<sl-breadcrumb-item>Shirts &amp; Tops</sl-breadcrumb-item>
</sl-breadcrumb>
```
## Examples
### Breadcrumb Links
By default, breadcrumb items are rendered as buttons so you can use them to navigate single-page applications. In this case, you'll need to add event listeners to handle clicks.
For websites, you'll probably want to use links instead. You can make any breadcrumb item a link by applying an `href` attribute to it. Now, when the user activates it, they'll be taken to the corresponding page — no event listeners required.
```html preview
<sl-breadcrumb>
<sl-breadcrumb-item href="https://example.com/home">
Homepage
</sl-breadcrumb-item>
<sl-breadcrumb-item href="https://example.com/home/services">
Our Services
</sl-breadcrumb-item>
<sl-breadcrumb-item href="https://example.com/home/services/digital">
Digital Media
</sl-breadcrumb-item>
<sl-breadcrumb-item href="https://example.com/home/services/digital/web-design">
Web Design
</sl-breadcrumb-item>
</sl-breadcrumb>
```
### Custom Separators
Use the `separator` slot to change the separator that goes between breadcrumb items. Icons work well, but you can also use text or an image.
```html preview
<sl-breadcrumb>
<sl-icon name="dot" slot="separator"></sl-icon>
<sl-breadcrumb-item>First</sl-breadcrumb-item>
<sl-breadcrumb-item>Second</sl-breadcrumb-item>
<sl-breadcrumb-item>Third</sl-breadcrumb-item>
</sl-breadcrumb>
<br>
<sl-breadcrumb>
<sl-icon name="arrow-right" slot="separator"></sl-icon>
<sl-breadcrumb-item>First</sl-breadcrumb-item>
<sl-breadcrumb-item>Second</sl-breadcrumb-item>
<sl-breadcrumb-item>Third</sl-breadcrumb-item>
</sl-breadcrumb>
<br>
<sl-breadcrumb>
<span slot="separator">/</span>
<sl-breadcrumb-item>First</sl-breadcrumb-item>
<sl-breadcrumb-item>Second</sl-breadcrumb-item>
<sl-breadcrumb-item>Third</sl-breadcrumb-item>
</sl-breadcrumb>
```
### Prefixes
Use the `prefix` slot to add content before any breadcrumb item.
```html preview
<sl-breadcrumb>
<sl-breadcrumb-item>
<sl-icon slot="prefix" name="house"></sl-icon>
Home
</sl-breadcrumb-item>
<sl-breadcrumb-item>Articles</sl-breadcrumb-item>
<sl-breadcrumb-item>Traveling</sl-breadcrumb-item>
</sl-breadcrumb>
```
### Suffixes
Use the `suffix` slot to add content after any breadcrumb item.
```html preview
<sl-breadcrumb>
<sl-breadcrumb-item>Documents</sl-breadcrumb-item>
<sl-breadcrumb-item>Policies</sl-breadcrumb-item>
<sl-breadcrumb-item>
Security
<sl-icon slot="suffix" name="shield-lock"></sl-icon>
</sl-breadcrumb-item>
</sl-breadcrumb>
```
### With Dropdowns
Dropdown menus can be placed in a prefix or suffix slot to provide additional options.
```html preview
<sl-breadcrumb>
<sl-breadcrumb-item>Homepage</sl-breadcrumb-item>
<sl-breadcrumb-item>Our Services</sl-breadcrumb-item>
<sl-breadcrumb-item>Digital Media</sl-breadcrumb-item>
<sl-breadcrumb-item>
Web Design
<sl-dropdown slot="suffix">
<sl-button slot="trigger" size="small" circle>
<sl-icon label="More options" name="three-dots"></sl-icon>
</sl-button>
<sl-menu>
<sl-menu-item checked>Web Design</sl-menu-item>
<sl-menu-item>Web Development</sl-menu-item>
<sl-menu-item>Marketing</sl-menu-item>
</sl-menu>
</sl-dropdown>
</sl-breadcrumb-item>
</sl-breadcrumb>
```
[component-metadata:sl-breadcrumb]

View File

@@ -1,221 +0,0 @@
# Button Group
[component-header:sl-button-group]
Button groups can be used to group related buttons into sections.
```html preview
<sl-button-group>
<sl-button>Left</sl-button>
<sl-button>Center</sl-button>
<sl-button>Right</sl-button>
</sl-button-group>
```
## Examples
### Button Sizes
All button sizes are supported, but avoid mixing sizes within the same button group.
```html preview
<sl-button-group>
<sl-button size="small">Left</sl-button>
<sl-button size="small">Center</sl-button>
<sl-button size="small">Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button size="medium">Left</sl-button>
<sl-button size="medium">Center</sl-button>
<sl-button size="medium">Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button size="large">Left</sl-button>
<sl-button size="large">Center</sl-button>
<sl-button size="large">Right</sl-button>
</sl-button-group>
```
### Theme Buttons
Theme buttons are supported through the button's `type` attribute.
```html preview
<sl-button-group>
<sl-button type="primary">Left</sl-button>
<sl-button type="primary">Center</sl-button>
<sl-button type="primary">Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button type="success">Left</sl-button>
<sl-button type="success">Center</sl-button>
<sl-button type="success">Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button type="neutral">Left</sl-button>
<sl-button type="neutral">Center</sl-button>
<sl-button type="neutral">Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button type="warning">Left</sl-button>
<sl-button type="warning">Center</sl-button>
<sl-button type="warning">Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button type="danger">Left</sl-button>
<sl-button type="danger">Center</sl-button>
<sl-button type="danger">Right</sl-button>
</sl-button-group>
```
### Pill Buttons
Pill buttons are supported through the button's `pill` attribute.
```html preview
<sl-button-group>
<sl-button size="small" pill>Left</sl-button>
<sl-button size="small" pill>Center</sl-button>
<sl-button size="small" pill>Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button size="medium" pill>Left</sl-button>
<sl-button size="medium" pill>Center</sl-button>
<sl-button size="medium" pill>Right</sl-button>
</sl-button-group>
<br><br>
<sl-button-group>
<sl-button size="large" pill>Left</sl-button>
<sl-button size="large" pill>Center</sl-button>
<sl-button size="large" pill>Right</sl-button>
</sl-button-group>
```
### Dropdowns in Button Groups
Dropdowns can be placed inside button groups as long as the trigger is an `<sl-button>` element.
```html preview
<sl-button-group>
<sl-button>Button</sl-button>
<sl-button>Button</sl-button>
<sl-dropdown>
<sl-button slot="trigger" caret>Dropdown</sl-button>
<sl-menu>
<sl-menu-item>Item 1</sl-menu-item>
<sl-menu-item>Item 2</sl-menu-item>
<sl-menu-item>Item 3</sl-menu-item>
</sl-menu>
</sl-dropdown>
</sl-button-group>
```
### Split Buttons
Create a split button using a button and a dropdown.
```html preview
<sl-button-group>
<sl-button type="primary">Save</sl-button>
<sl-dropdown placement="bottom-end">
<sl-button slot="trigger" type="primary" caret></sl-button>
<sl-menu>
<sl-menu-item>Save</sl-menu-item>
<sl-menu-item>Save as&hellip;</sl-menu-item>
<sl-menu-item>Save all</sl-menu-item>
</sl-menu>
</sl-dropdown>
</sl-button-group>
```
### Tooltips in Button Groups
Buttons can be wrapped in tooltips to provide more detail when the user interacts with them.
```html preview
<sl-button-group>
<sl-tooltip content="I'm on the left">
<sl-button>Left</sl-button>
</sl-tooltip>
<sl-tooltip content="I'm in the middle">
<sl-button>Center</sl-button>
</sl-tooltip>
<sl-tooltip content="I'm on the right">
<sl-button>Right</sl-button>
</sl-tooltip>
</sl-button-group>
```
### Toolbar Example
Create interactive toolbars with button groups.
```html preview
<div class="button-group-toolbar">
<sl-button-group label="History">
<sl-tooltip content="Undo">
<sl-button><sl-icon name="arrow-counterclockwise"></sl-icon></sl-button>
</sl-tooltip>
<sl-tooltip content="Redo">
<sl-button><sl-icon name="arrow-clockwise"></sl-icon></sl-button>
</sl-tooltip>
</sl-button-group>
<sl-button-group label="Formatting">
<sl-tooltip content="Bold">
<sl-button><sl-icon name="type-bold"></sl-icon></sl-button>
</sl-tooltip>
<sl-tooltip content="Italic">
<sl-button><sl-icon name="type-italic"></sl-icon></sl-button>
</sl-tooltip>
<sl-tooltip content="Underline">
<sl-button><sl-icon name="type-underline"></sl-icon></sl-button>
</sl-tooltip>
</sl-button-group>
<sl-button-group label="Alignment">
<sl-tooltip content="Align Left">
<sl-button><sl-icon name="justify-left"></sl-icon></sl-button>
</sl-tooltip>
<sl-tooltip content="Align Center">
<sl-button><sl-icon name="justify"></sl-icon></sl-button>
</sl-tooltip>
<sl-tooltip content="Align Right">
<sl-button><sl-icon name="justify-right"></sl-icon></sl-button>
</sl-tooltip>
</sl-button-group>
</div>
<style>
.button-group-toolbar sl-button-group:not(:last-of-type) {
margin-right: var(--sl-spacing-x-small);
}
</style>
```
[component-metadata:sl-button-group]

View File

@@ -1,240 +0,0 @@
# Button
[component-header:sl-button]
Buttons represent actions that are available to the user.
```html preview
<sl-button>Button</sl-button>
```
## Examples
### Types
Use the `type` attribute to set the button's type.
```html preview
<sl-button type="default">Default</sl-button>
<sl-button type="primary">Primary</sl-button>
<sl-button type="success">Success</sl-button>
<sl-button type="neutral">Neutral</sl-button>
<sl-button type="warning">Warning</sl-button>
<sl-button type="danger">Danger</sl-button>
```
### Sizes
Use the `size` attribute to change a button's size.
```html preview
<sl-button size="small">Small</sl-button>
<sl-button size="medium">Medium</sl-button>
<sl-button size="large">Large</sl-button>
```
### Outline Buttons
Use the `outline` attribute to draw outlined buttons with transparent backgrounds.
```html preview
<sl-button type="default" outline>Default</sl-button>
<sl-button type="primary" outline>Primary</sl-button>
<sl-button type="success" outline>Success</sl-button>
<sl-button type="neutral" outline>Neutral</sl-button>
<sl-button type="warning" outline>Warning</sl-button>
<sl-button type="danger" outline>Danger</sl-button>
```
### Pill Buttons
Use the `pill` attribute to give buttons rounded edges.
```html preview
<sl-button size="small" pill>Small</sl-button>
<sl-button size="medium" pill>Medium</sl-button>
<sl-button size="large" pill>Large</sl-button>
```
### Circle Buttons
Use the `circle` attribute to create circular icon buttons.
```html preview
<sl-button type="default" size="small" circle><sl-icon name="gear"></sl-icon></sl-button>
<sl-button type="default" size="medium" circle><sl-icon name="gear"></sl-icon></sl-button>
<sl-button type="default" size="large" circle><sl-icon name="gear"></sl-icon></sl-button>
```
### Text Buttons
Use the `text` type to create text buttons that share the same size as regular buttons but don't have backgrounds or borders.
```html preview
<sl-button type="text" size="small">Text</sl-button>
<sl-button type="text" size="medium">Text</sl-button>
<sl-button type="text" size="large">Text</sl-button>
```
### Link Buttons
It's often helpful to have a button that works like a link. This is possible by setting the `href` attribute, which will make the component render an `<a>` under the hood. This gives you all the default link behavior the browser provides (e.g. <kbd>CMD/CTRL/SHIFT + CLICK</kbd>) and exposes the `target` and `download` attributes.
```html preview
<sl-button href="https://example.com/">Link</sl-button>
<sl-button href="https://example.com/" target="_blank">New Window</sl-button>
<sl-button href="/assets/images/wordmark.svg" download="shoelace.svg">Download</sl-button>
<sl-button href="https://example.com/" disabled>Disabled</sl-button>
```
?> When a `target` is set, the link will receive `rel="noreferrer noopener"` for [security reasons](https://mathiasbynens.github.io/rel-noopener/).
### Setting a Custom Width
As expected, buttons can be given a custom width by setting its `width`. This is useful for making buttons span the full width of their container on smaller screens.
```html preview
<sl-button type="default" size="small" style="width: 100%; margin-bottom: 1rem;">Small</sl-button>
<sl-button type="default" size="medium" style="width: 100%; margin-bottom: 1rem;">Medium</sl-button>
<sl-button type="default" size="large" style="width: 100%;">Large</sl-button>
```
### Prefix and Suffix Icons
Use the `prefix` and `suffix` slots to add icons.
```html preview
<sl-button type="default" size="small">
<sl-icon slot="prefix" name="gear"></sl-icon>
Settings
</sl-button>
<sl-button type="default" size="small">
<sl-icon slot="suffix" name="arrow-counterclockwise"></sl-icon>
Refresh
</sl-button>
<sl-button type="default" size="small">
<sl-icon slot="prefix" name="link-45deg"></sl-icon>
<sl-icon slot="suffix" name="box-arrow-up-right"></sl-icon>
Open
</sl-button>
<br><br>
<sl-button type="default">
<sl-icon slot="prefix" name="gear"></sl-icon>
Settings
</sl-button>
<sl-button type="default">
<sl-icon slot="suffix" name="arrow-counterclockwise"></sl-icon>
Refresh
</sl-button>
<sl-button type="default">
<sl-icon slot="prefix" name="link-45deg"></sl-icon>
<sl-icon slot="suffix" name="box-arrow-up-right"></sl-icon>
Open
</sl-button>
<br><br>
<sl-button type="default" size="large">
<sl-icon slot="prefix" name="gear"></sl-icon>
Settings
</sl-button>
<sl-button type="default" size="large">
<sl-icon slot="suffix" name="arrow-counterclockwise"></sl-icon>
Refresh
</sl-button>
<sl-button type="default" size="large">
<sl-icon slot="prefix" name="link-45deg"></sl-icon>
<sl-icon slot="suffix" name="box-arrow-up-right"></sl-icon>
Open
</sl-button>
```
### Caret
Use the `caret` attribute to add a dropdown indicator when a button will trigger a dropdown, menu, or popover.
```html preview
<sl-button size="small" caret>Small</sl-button>
<sl-button size="medium" caret>Medium</sl-button>
<sl-button size="large" caret>Large</sl-button>
```
### Loading
Use the `loading` attribute to make a button busy. The width will remain the same as before, preventing adjacent elements from moving around. Clicks will be suppressed until the loading state is removed.
```html preview
<sl-button type="default" loading>Default</sl-button>
<sl-button type="primary" loading>Primary</sl-button>
<sl-button type="success" loading>Success</sl-button>
<sl-button type="neutral" loading>Neutral</sl-button>
<sl-button type="warning" loading>Warning</sl-button>
<sl-button type="danger" loading>Danger</sl-button>
```
### Disabled
Use the `disabled` attribute to disable a button. Clicks will be suppressed until the disabled state is removed.
```html preview
<sl-button type="default" disabled>Default</sl-button>
<sl-button type="primary" disabled>Primary</sl-button>
<sl-button type="success" disabled>Success</sl-button>
<sl-button type="neutral" disabled>Neutral</sl-button>
<sl-button type="warning" disabled>Warning</sl-button>
<sl-button type="danger" disabled>Danger</sl-button>
```
### Styling Buttons
This example demonstrates how to style buttons using a custom class. This is the recommended approach if you need to add additional variations. To customize an existing variation, modify the selector to target the button's type attribute instead of a class (e.g. `sl-button[type="primary"]`).
```html preview
<sl-button class="pink">Pink Button</sl-button>
<style>
sl-button.pink::part(base) {
/* Set design tokens for height and border width */
--sl-input-height-medium: 48px;
--sl-input-border-width: 4px;
border-radius: 0;
background-color: #ff1493;
border-top-color: #ff7ac1;
border-left-color: #ff7ac1;
border-bottom-color: #ad005c;
border-right-color: #ad005c;
color: white;
font-size: 1.125rem;
box-shadow: 0 2px 10px #0002;
transition: var(--sl-transition-medium) transform ease, var(--sl-transition-medium) border ease;
}
sl-button.pink::part(base):hover {
transform: scale(1.05) rotate(-1deg);
}
sl-button.pink::part(base):active {
border-top-color: #ad005c;
border-right-color: #ff7ac1;
border-bottom-color: #ff7ac1;
border-left-color: #ad005c;
transform: scale(1.05) rotate(-1deg) translateY(2px);
}
sl-button.pink::part(base):focus-visible {
outline: dashed 2px deeppink;
outline-offset: 4px;
}
</style>
```
[component-metadata:sl-button]

View File

@@ -1,144 +0,0 @@
# Card
[component-header:sl-card]
Cards can be used to group related subjects in a container.
```html preview
<sl-card class="card-overview">
<img
slot="image"
src="https://images.unsplash.com/photo-1559209172-0ff8f6d49ff7?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=500&q=80"
alt="A kitten sits patiently between a terracotta pot and decorative grasses."
>
<strong>Mittens</strong><br>
This kitten is as cute as he is playful. Bring him home today!<br>
<small>6 weeks old</small>
<div slot="footer">
<sl-button type="primary" pill>More Info</sl-button>
<sl-rating></sl-rating>
</div>
</sl-card>
<style>
.card-overview {
max-width: 300px;
}
.card-overview small {
color: rgb(var(--sl-color-neutral-500));
}
.card-overview [slot="footer"] {
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
```
## Examples
## Basic Card
Basic cards aren't very exciting, but they can display any content you want them to.
```html preview
<sl-card class="card-basic">
This is just a basic card. No image, no header, and no footer. Just your content.
</sl-card>
<style>
.card-basic {
max-width: 300px;
}
</style>
```
## Card with Header
Headers can be used to display titles and more.
```html preview
<sl-card class="card-header">
<div slot="header">
Header Title
<sl-icon-button name="gear"></sl-icon-button>
</div>
This card has a header. You can put all sorts of things in it!
</sl-card>
<style>
.card-header {
max-width: 300px;
}
.card-header [slot="header"] {
display: flex;
align-items: center;
justify-content: space-between;
}
.card-header h3 {
margin: 0;
}
.card-header sl-icon-button {
font-size: var(--sl-font-size-medium);
}
</style>
```
## Card with Footer
Footers can be used to display actions, summaries, or other relevant content.
```html preview
<sl-card class="card-footer">
This card has a footer. You can put all sorts of things in it!
<div slot="footer">
<sl-rating></sl-rating>
<sl-button slot="footer" type="primary">Preview</sl-button>
</div>
</sl-card>
<style>
.card-footer {
max-width: 300px;
}
.card-footer [slot="footer"] {
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
```
## Images
Cards accept an `image` slot. The image is displayed atop the card and stretches to fit.
```html preview
<sl-card class="card-image">
<img
slot="image"
src="https://images.unsplash.com/photo-1547191783-94d5f8f6d8b1?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=400&q=80"
alt="A kitten walks towards camera on top of pallet."
>
This is a kitten, but not just any kitten. This kitten likes walking along pallets.
</sl-card>
<style>
.card-image {
max-width: 300px;
}
</style>
```
[component-metadata:sl-card]

View File

@@ -1,39 +0,0 @@
# Checkbox
[component-header:sl-checkbox]
Checkboxes allow the user to toggle an option on or off.
```html preview
<sl-checkbox>Checkbox</sl-checkbox>
```
?> This component doesn't work with standard forms. Use [`<sl-form>`](/components/form) instead.
## Examples
### Checked
Use the `checked` attribute to activate the checkbox.
```html preview
<sl-checkbox checked>Checked</sl-checkbox>
```
### Indeterminate
Use the `indeterminate` attribute to make the checkbox indeterminate.
```html preview
<sl-checkbox indeterminate>Indeterminate</sl-checkbox>
```
### Disabled
Use the `disabled` attribute to disable the checkbox.
```html preview
<sl-checkbox disabled>Disabled</sl-checkbox>
```
[component-metadata:sl-checkbox]

View File

@@ -1,52 +0,0 @@
# Color Picker
[component-header:sl-color-picker]
Color pickers allow the user to select a color.
```html preview
<sl-color-picker></sl-color-picker>
```
## Examples
### Opacity
Use the `opacity` attribute to enable the opacity slider. When this is enabled, the value will be displayed as HEXA, RGBA, or HSLA based on `format`.
```html preview
<sl-color-picker opacity></sl-color-picker>
```
### Formats
Set the color picker's format with the `format` attribute. Valid options include `hex`, `rgb`, and `hsl`. Note that the color picker's input will accept any parsable format (including CSS color names) regardless of this option.
To prevent users from toggling the format themselves, add the `no-format-toggle` attribute.
```html preview
<sl-color-picker format="hex" value="#4a90e2"></sl-color-picker>
<sl-color-picker format="rgb" value="rgb(80, 227, 194)"></sl-color-picker>
<sl-color-picker format="hsl" value="hsl(290, 87%, 47%)"></sl-color-picker>
```
### Sizes
Use the `size` attribute to change the color picker's trigger size.
```html preview
<sl-color-picker size="small"></sl-color-picker>
<sl-color-picker size="medium"></sl-color-picker>
<sl-color-picker size="large"></sl-color-picker>
```
### Inline
The color picker can be rendered inline instead of in a dropdown using the `inline` attribute.
```html preview
<sl-color-picker inline></sl-color-picker>
```
[component-metadata:sl-color-picker]

View File

@@ -1,140 +0,0 @@
# Context Menu
[component-header:sl-context-menu]
Context menus offer additional options through a menu that opens at the pointer's location, usually activated by a right-click.
Context menus are designed to work with [menus](/components/menu) and [menu items](/components/menu-item). The menu must include `slot="menu"`. Other content you provide will be part of the context menu's target area.
```html preview
<sl-context-menu>
<div style="height: 200px; background: rgb(var(--sl-color-neutral-100)); display: flex; align-items: center; justify-content: center; padding: 1rem;">
Right-click to activate the context menu
</div>
<sl-menu slot="menu">
<sl-menu-item value="undo">Undo</sl-menu-item>
<sl-menu-item value="redo">Redo</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
<sl-menu-item value="delete">Delete</sl-menu-item>
</sl-menu>
</sl-context-menu>
```
## Examples
### Handling Selections
The [menu component](/components/menu) emits an `sl-select` event when a menu item is selected. You can use this to handle selections. The selected item will be available in `event.detail.item`.
```html preview
<div class="context-menu-selections">
<sl-context-menu>
<div style="height: 200px; background: rgb(var(--sl-color-neutral-100)); display: flex; align-items: center; justify-content: center; padding: 1rem;">
Right-click to activate the context menu
</div>
<sl-menu slot="menu">
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
</sl-menu>
</sl-context-menu>
</div>
<script>
const container = document.querySelector('.context-menu-selections');
const menu = container.querySelector('sl-menu');
const result = container.querySelector('.result');
menu.addEventListener('sl-select', event => {
console.log(`You selected: ${event.detail.item.value}`);
});
</script>
```
### Inline
The context menu uses `display: contents`, so it will assume the shape of the content you slot in.
```html preview
<sl-context-menu>
<span style="background: rgb(var(--sl-color-neutral-100)); padding: .5rem 1rem;">
Right-click here
</span>
<sl-menu slot="menu">
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
</sl-menu>
</sl-context-menu>
```
### Placement
The preferred placement of the context menu can be set with the `placement` attribute. Note that the actual position may vary to ensure the menu remains in the viewport.
```html preview
<sl-context-menu placement="top-end">
<div style="height: 200px; background: rgb(var(--sl-color-neutral-100)); display: flex; align-items: center; justify-content: center; padding: 1rem;">
Right-click to activate the context menu
</div>
<sl-menu slot="menu">
<sl-menu-item value="undo">Undo</sl-menu-item>
<sl-menu-item value="redo">Redo</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
<sl-menu-item value="delete">Delete</sl-menu-item>
</sl-menu>
</sl-context-menu>
```
### Detecting the Target Item
A single context menu can wrap a number of items. To detect the item that activated the context menu...
TODO
```html preview
<div class="context-menu-detecting">
<sl-context-menu>
<ul>
<li>Item 1</li>
<li>Item 2</li>
<li>Item 3</li>
<li>Item 4</li>
<li>Item 5</li>
</ul>
<sl-menu slot="menu">
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
</sl-menu>
</sl-context-menu>
</div>
<style>
.context-menu-detecting ul {
max-width: 300px;
list-style: none;
padding: 0;
margin: 0;
}
.context-menu-detecting li {
background: rgb(var(--sl-color-neutral-100));
padding: .5rem 1rem;
margin: 0 0 2px 0;
}
</style>
```
[component-metadata:sl-context-menu]

View File

@@ -1,65 +0,0 @@
# Details
[component-header:sl-details]
Details show a brief summary and expand to show additional content.
```html preview
<sl-details summary="Toggle Me">
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna
aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
</sl-details>
```
## Examples
### Disabled
Use the `disable` attribute to prevent the details from expanding.
```html preview
<sl-details summary="Disabled" disabled>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna
aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
</sl-details>
```
### Grouping Details
Details are designed to function independently, but you can simulate a group or "accordion" where only one is shown at a time by listening for the `sl-show` event.
```html preview
<div class="details-group-example">
<sl-details summary="First" open>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna
aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
</sl-details>
<sl-details summary="Second">
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna
aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
</sl-details>
<sl-details summary="Third">
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna
aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.
</sl-details>
</div>
<script>
const container = document.querySelector('.details-group-example');
// Close all other details when one is shown
container.addEventListener('sl-show', event => {
[...container.querySelectorAll('sl-details')].map(details => (details.open = event.target === details));
});
</script>
<style>
.details-group-example sl-details:not(:last-of-type) {
margin-bottom: var(--sl-spacing-2x-small);
}
</style>
```
[component-metadata:sl-details]

View File

@@ -1,133 +0,0 @@
# Dialog
[component-header:sl-dialog]
Dialogs, sometimes called "modals", appear above the page and require the user's immediate attention.
```html preview
<sl-dialog label="Dialog" class="dialog-overview">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-dialog>
<sl-button>Open Dialog</sl-button>
<script>
const dialog = document.querySelector('.dialog-overview');
const openButton = dialog.nextElementSibling;
const closeButton = dialog.querySelector('sl-button[slot="footer"]');
openButton.addEventListener('click', () => dialog.show());
closeButton.addEventListener('click', () => dialog.hide());
</script>
```
## UX Tips
- Use a dialog when you immediately require the user's attention, e.g. confirming a destructive action.
- Always provide an obvious way for the user to dismiss the dialog.
- Don't nest dialogs. It almost always leads to a poor experience for the user.
## Examples
### Custom Width
Use the `--width` custom property to set the dialog's width.
```html preview
<sl-dialog label="Dialog" class="dialog-width" style="--width: 50vw;">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-dialog>
<sl-button>Open Dialog</sl-button>
<script>
const dialog = document.querySelector('.dialog-width');
const openButton = dialog.nextElementSibling;
const closeButton = dialog.querySelector('sl-button[slot="footer"]');
openButton.addEventListener('click', () => dialog.show());
closeButton.addEventListener('click', () => dialog.hide());
</script>
```
### Scrolling
By design, a dialog's height will never exceed that of the viewport. As such, dialogs will not scroll with the page ensuring the header and footer are always accessible to the user.
```html preview
<sl-dialog label="Dialog" class="dialog-scrolling">
<div style="height: 150vh; border: dashed 2px rgb(var(--sl-color-neutral-200)); padding: 0 1rem;">
<p>Scroll down and give it a try! 👇</p>
</div>
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-dialog>
<sl-button>Open Dialog</sl-button>
<script>
const dialog = document.querySelector('.dialog-scrolling');
const openButton = dialog.nextElementSibling;
const closeButton = dialog.querySelector('sl-button[slot="footer"]');
openButton.addEventListener('click', () => dialog.show());
closeButton.addEventListener('click', () => dialog.hide());
</script>
```
### Preventing the Dialog from Closing
By default, dialogs will close when the user clicks the close button, clicks the overlay, or presses the <kbd>Escape</kbd> key. In most cases, the default behavior is the best behavior in terms of UX. However, there are situations where this may be undesirable, such as when data loss will occur.
To keep the dialog open in such cases, you can cancel the `sl-request-close` event. When canceled, the dialog will remain open and pulse briefly to draw the user's attention to it.
```html preview
<sl-dialog label="Dialog" class="dialog-deny-close">
This dialog will not close unless you use the button below.
<sl-button slot="footer" type="primary">Save &amp; Close</sl-button>
</sl-dialog>
<sl-button>Open Dialog</sl-button>
<script>
const dialog = document.querySelector('.dialog-deny-close');
const openButton = dialog.nextElementSibling;
const saveButton = dialog.querySelector('sl-button[slot="footer"]');
openButton.addEventListener('click', () => dialog.show());
saveButton.addEventListener('click', () => dialog.hide());
dialog.addEventListener('sl-request-close', event => event.preventDefault());
</script>
```
### Customizing Initial Focus
By default, the dialog's panel will gain focus when opened. This allows the first tab press to focus on the first tabbable element within the dialog. To set focus on a different element, listen for and cancel the `sl-initial-focus` event.
```html preview
<sl-dialog label="Dialog" class="dialog-focus">
<sl-input placeholder="I will have focus when the dialog is opened"></sl-input>
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-dialog>
<sl-button>Open Dialog</sl-button>
<script>
const dialog = document.querySelector('.dialog-focus');
const input = dialog.querySelector('sl-input');
const openButton = dialog.nextElementSibling;
const closeButton = dialog.querySelector('sl-button[slot="footer"]');
openButton.addEventListener('click', () => dialog.show());
closeButton.addEventListener('click', () => dialog.hide());
dialog.addEventListener('sl-initial-focus', event => {
event.preventDefault();
input.focus({ preventScroll: true });
});
</script>
```
[component-metadata:sl-dialog]

View File

@@ -1,71 +0,0 @@
# Divider
[component-header:sl-divider]
Dividers are used to visually separate or group elements.
```html preview
<sl-divider></sl-divider>
```
## Examples
### Width
Use the `--width` custom property to change the width of the divider.
```html preview
<sl-divider style="--width: 4px;"></sl-divider>
```
### Color
Use the `--color` custom property to change the color of the divider.
```html preview
<sl-divider style="--color: tomato;"></sl-divider>
```
### Spacing
Use the `--spacing` custom property to change the amount of space between the divider and it's neighboring elements.
```html preview
<div style="text-align: center;">
Above
<sl-divider style="--spacing: 2rem;"></sl-divider>
Below
</div>
```
### Vertical
Add the `vertical` attribute to draw the divider in a vertical orientation. The divider will span the full height of its container. Vertical dividers work especially well inside of a flex container.
```html preview
<div style="display: flex; align-items: center; height: 2rem;">
First
<sl-divider vertical></sl-divider>
Middle
<sl-divider vertical></sl-divider>
Last
</div>
```
### Menu Dividers
Use dividers in [menus](/components/menu) to visually group menu items.
```html preview
<sl-menu style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item value="1">Option 1</sl-menu-item>
<sl-menu-item value="2">Option 2</sl-menu-item>
<sl-menu-item value="3">Option 3</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item value="4">Option 4</sl-menu-item>
<sl-menu-item value="5">Option 5</sl-menu-item>
<sl-menu-item value="6">Option 6</sl-menu-item>
</sl-menu>
```
[component-metadata:sl-divider]

View File

@@ -1,222 +0,0 @@
# Drawer
[component-header:sl-drawer]
Drawers slide in from a container to expose additional options and information.
```html preview
<sl-drawer label="Drawer" class="drawer-overview">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-overview');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
## Examples
### Slide in From Start
By default, drawers slide in from the end. To make the drawer slide in from the start, set the `placement` attribute to `start`.
```html preview
<sl-drawer label="Drawer" placement="start" class="drawer-placement-start">
This drawer slides in from the start.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-placement-start');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
### Slide in From Top
To make the drawer slide in from the top, set the `placement` attribute to `top`.
```html preview
<sl-drawer label="Drawer" placement="top" class="drawer-placement-top">
This drawer slides in from the top.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-placement-top');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
### Slide in From Bottom
To make the drawer slide in from the bottom, set the `placement` attribute to `bottom`.
```html preview
<sl-drawer label="Drawer" placement="bottom" class="drawer-placement-bottom">
This drawer slides in from the bottom.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-placement-bottom');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
### Contained to an Element
By default, the drawer slides out of its [containing block](https://developer.mozilla.org/en-US/docs/Web/CSS/Containing_block#Identifying_the_containing_block), which is usually the viewport. To make the drawer slide out of its parent element, add the `contained` attribute and `position: relative` to the parent.
```html preview
<div
style="position: relative; border: solid 2px rgb(var(--sl-panel-border-color)); height: 300px; padding: 1rem; margin-bottom: 1rem;"
>
The drawer will be contained to this box. This content won't shift or be affected in any way when the drawer opens.
<sl-drawer label="Drawer" contained class="drawer-contained" style="--size: 50%;">
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
</div>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-contained');
const openButton = drawer.parentElement.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
### Custom Size
Use the `--size` custom property to set the drawer's size. This will be applied to the drawer's width or height depending on its `placement`.
```html preview
<sl-drawer label="Drawer" class="drawer-custom-size" style="--size: 50vw;">
This drawer is always 50% of the viewport.
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-custom-size');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
### Scrolling
By design, a drawer's height will never exceed 100% of its container. As such, drawers will not scroll with the page to ensure the header and footer are always accessible to the user.
```html preview
<sl-drawer label="Drawer" class="drawer-scrolling">
<div style="height: 150vh; border: dashed 2px rgb(var(--sl-color-neutral-200)); padding: 0 1rem;">
<p>Scroll down and give it a try! 👇</p>
</div>
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-scrolling');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
</script>
```
### Preventing the Drawer from Closing
By default, drawers will close when the user clicks the close button, clicks the overlay, or presses the <kbd>Escape</kbd> key. In most cases, the default behavior is the best behavior in terms of UX. However, there are situations where this may be undesirable, such as when data loss will occur.
To keep the drawer open in such cases, you can cancel the `sl-request-close` event. When canceled, the drawer will remain open and pulse briefly to draw the user's attention to it.
```html preview
<sl-drawer label="Drawer" class="drawer-deny-close">
This dialog will not close unless you use the button below.
<sl-button slot="footer" type="primary">Save &amp; Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-deny-close');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
drawer.addEventListener('sl-request-close', event => event.preventDefault());
</script>
```
### Customizing Initial Focus
By default, the drawer's panel will gain focus when opened. This allows the first tab press to focus on the first tabbable element within the drawer. To set focus on a different element, listen for and cancel the `sl-initial-focus` event.
```html preview
<sl-drawer label="Drawer" class="drawer-focus">
<sl-input placeholder="I will have focus when the drawer is opened"></sl-input>
<sl-button slot="footer" type="primary">Close</sl-button>
</sl-drawer>
<sl-button>Open Drawer</sl-button>
<script>
const drawer = document.querySelector('.drawer-focus');
const input = drawer.querySelector('sl-input');
const openButton = drawer.nextElementSibling;
const closeButton = drawer.querySelector('sl-button[type="primary"]');
openButton.addEventListener('click', () => drawer.show());
closeButton.addEventListener('click', () => drawer.hide());
drawer.addEventListener('sl-initial-focus', event => {
event.preventDefault();
input.focus({ preventScroll: true });
});
</script>
```
[component-metadata:sl-drawer]

View File

@@ -1,151 +0,0 @@
# Dropdown
[component-header:sl-dropdown]
Dropdowns expose additional content that "drops down" in a panel.
Dropdowns consist of a trigger and a panel. By default, activating the trigger will expose the panel and interacting outside of the panel will close it.
Dropdowns are designed to work well with [menus](/components/menu) to provide a list of options the user can select from. However, dropdowns can also be used in lower-level applications (e.g. [color picker](/components/color-picker) and [select](/components/select)). The API gives you complete control over showing, hiding, and positioning the panel.
```html preview
<sl-dropdown>
<sl-button slot="trigger" caret>Dropdown</sl-button>
<sl-menu>
<sl-menu-item>Dropdown Item 1</sl-menu-item>
<sl-menu-item>Dropdown Item 2</sl-menu-item>
<sl-menu-item>Dropdown Item 3</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item checked>Checked</sl-menu-item>
<sl-menu-item disabled>Disabled</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item>
Prefix
<sl-icon slot="prefix" name="gift"></sl-icon>
</sl-menu-item>
<sl-menu-item>
Suffix Icon
<sl-icon slot="suffix" name="heart"></sl-icon>
</sl-menu-item>
</sl-menu>
</sl-dropdown>
```
## Examples
### Getting the Selected Item
When dropdowns are used with [menus](/components/menu), you can listen for the `sl-select` event to determine which menu item was selected. The menu item element will be exposed in `event.detail.item`. You can set `value` props to make it easier to identify commands.
```html preview
<div class="dropdown-selection">
<sl-dropdown>
<sl-button slot="trigger" caret>Edit</sl-button>
<sl-menu>
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
</sl-menu>
</sl-dropdown>
</div>
<script>
const container = document.querySelector('.dropdown-selection');
const dropdown = container.querySelector('sl-dropdown');
dropdown.addEventListener('sl-select', event => {
const selectedItem = event.detail.item;
console.log(selectedItem.value);
});
</script>
```
### Placement
The preferred placement of the dropdown can be set with the `placement` attribute. Note that the actual position may vary to ensure the panel remains in the viewport.
```html preview
<sl-dropdown placement="top-start">
<sl-button slot="trigger" caret>Edit</sl-button>
<sl-menu>
<sl-menu-item>Cut</sl-menu-item>
<sl-menu-item>Copy</sl-menu-item>
<sl-menu-item>Paste</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item>Find</sl-menu-item>
<sl-menu-item>Replace</sl-menu-item>
</sl-menu>
</sl-dropdown>
```
### Distance
The distance from the panel to the trigger can be customized using the `distance` attribute. This value is specified in pixels.
```html preview
<sl-dropdown distance="30">
<sl-button slot="trigger" caret>Edit</sl-button>
<sl-menu>
<sl-menu-item>Cut</sl-menu-item>
<sl-menu-item>Copy</sl-menu-item>
<sl-menu-item>Paste</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item>Find</sl-menu-item>
<sl-menu-item>Replace</sl-menu-item>
</sl-menu>
</sl-dropdown>
```
### Skidding
The offset of the panel along the trigger can be customized using the `skidding` attribute. This value is specified in pixels.
```html preview
<sl-dropdown skidding="30">
<sl-button slot="trigger" caret>Edit</sl-button>
<sl-menu>
<sl-menu-item>Cut</sl-menu-item>
<sl-menu-item>Copy</sl-menu-item>
<sl-menu-item>Paste</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item>Find</sl-menu-item>
<sl-menu-item>Replace</sl-menu-item>
</sl-menu>
</sl-dropdown>
```
### Hoisting
Dropdown panels will be clipped if they're inside a container that has `overflow: auto|hidden`. The `hoist` attribute forces the panel to use a fixed positioning strategy, allowing it to break out of the container. In this case, the panel will be positioned relative to its containing block, which is usually the viewport unless an ancestor uses a `transform`, `perspective`, or `filter`. [Refer to this page](https://developer.mozilla.org/en-US/docs/Web/CSS/position#fixed) for more details.
```html preview
<div class="dropdown-hoist">
<sl-dropdown>
<sl-button slot="trigger" caret>No Hoist</sl-button>
<sl-menu>
<sl-menu-item>Item 1</sl-menu-item>
<sl-menu-item>Item 2</sl-menu-item>
<sl-menu-item>Item 3</sl-menu-item>
</sl-menu>
</sl-dropdown>
<sl-dropdown hoist>
<sl-button slot="trigger" caret>Hoist</sl-button>
<sl-menu>
<sl-menu-item>Item 1</sl-menu-item>
<sl-menu-item>Item 2</sl-menu-item>
<sl-menu-item>Item 3</sl-menu-item>
</sl-menu>
</sl-dropdown>
</div>
<style>
.dropdown-hoist {
border: solid 2px rgb(var(--sl-panel-border-color));
padding: var(--sl-spacing-medium);
overflow: hidden;
}
</style>
```
[component-metadata:sl-dropdown]

View File

@@ -1,215 +0,0 @@
# Form
[component-header:sl-form]
Forms collect data that can easily be processed and sent to a server.
All Shoelace components make use of a [shadow DOM](https://developer.mozilla.org/en-US/docs/Web/Web_Components/Using_shadow_DOM) to encapsulate markup, styles, and behavior. One caveat of this approach is that native `<form>` elements will not recognize Shoelace form controls.
This component solves that problem by serializing _both_ Shoelace form controls and native form controls when the form is submitted. The resulting form data is exposed in the `sl-submit` event as a [`FormData`](https://developer.mozilla.org/en-US/docs/Web/API/FormData) object in `event.detail.formData`. You can also find an array of form controls in `event.detail.formControls`.
Shoelace forms don't make use of `action` and `method` attributes and they don't submit the same way as native forms. To handle submission, you need to listen for the `sl-submit` event as shown in the example below and make an XHR request with the resulting form data.
```html preview
<sl-form class="form-overview">
<sl-input name="name" type="text" label="Name"></sl-input>
<br>
<sl-select name="favorite" label="Select your favorite">
<sl-menu-item value="birds">Birds</sl-menu-item>
<sl-menu-item value="cats">Cats</sl-menu-item>
<sl-menu-item value="dogs">Dogs</sl-menu-item>
</sl-select>
<br>
<sl-checkbox name="agree" value="yes">
I totally agree
</sl-checkbox>
<br><br>
<sl-button submit>Submit</sl-button>
</sl-form>
<script>
const form = document.querySelector('.form-overview');
// Watch for the slSubmit event
form.addEventListener('sl-submit', event => {
const formData = event.detail.formData;
let output = '';
//
// Example 1: Post data to a server and wait for a JSON response
//
fetch('https://jsonplaceholder.typicode.com/posts', {
method: 'POST',
body: formData
})
.then(response => response.json())
.then(result => {
console.log('Success:', result);
})
.catch(error => {
console.error('Error:', error);
});
//
// Example 2: Output all form control names + values
//
for (const entry of formData.entries()) {
output += `${entry[0]}: ${entry[1]}\n`;
}
alert(output);
//
// Example 3: Get all form controls that were serialized as
// an array of HTML elements
//
console.log(event.detail.formControls);
});
</script>
```
## Form Control Validation
Client-side validation can be enabled through the browser's [Constraint Validation API](https://developer.mozilla.org/en-US/docs/Web/Guide/HTML/HTML5/Constraint_validation) for many form controls. You can enable it using props such as `required`, `pattern`, `minlength`, and `maxlength`. As the user interacts with the form control, the `invalid` attribute will reflect its validity based on its current value and the constraints that have been defined.
When a form control is invalid, the containing form will not be submitted. Instead, the browser will show the user a relevant error message. If you don't want to use client-side validation, you can suppress this behavior by adding `novalidate` to the `<sl-form>` element.
All form controls support validation, but not all validation props are available for every component. Refer to a component's documentation to see which validation props it supports.
!> Client-side validation can be used to improve the UX of forms, but it is not a replacement for server-side validation. **You should always validate and sanitize user input on the server!**
### Required Fields
To make a field required, use the `required` prop. The form will not be submitted if a required form control is empty.
```html preview
<sl-form class="input-validation-required">
<sl-input name="name" label="Name" required></sl-input>
<br>
<sl-select label="Favorite Animal" clearable required>
<sl-menu-item value="birds">Birds</sl-menu-item>
<sl-menu-item value="cats">Cats</sl-menu-item>
<sl-menu-item value="dogs">Dogs</sl-menu-item>
<sl-menu-item value="other">Other</sl-menu-item>
</sl-select>
<br>
<sl-textarea name="comment" label="Comment" required></sl-textarea>
<br>
<sl-checkbox required>Check me before submitting</sl-checkbox>
<br><br>
<sl-button type="primary" submit>Submit</sl-button>
</sl-form>
<script>
const form = document.querySelector('.input-validation-required');
form.addEventListener('sl-submit', () => alert('All fields are valid!'));
</script>
```
### Input Patterns
To restrict a value to a specific [pattern](https://developer.mozilla.org/en-US/docs/Web/HTML/Attributes/pattern), use the `pattern` attribute. This example only allows the letters A-Z, so the form will not submit if a number or symbol is entered. This only works with `<sl-input>` elements.
```html preview
<sl-form class="input-validation-pattern">
<sl-input name="letters" required label="Letters" pattern="[A-Za-z]+"></sl-input>
<br>
<sl-button type="primary" submit>Submit</sl-button>
</sl-form>
<script>
const form = document.querySelector('.input-validation-pattern');
form.addEventListener('sl-submit', () => alert('All fields are valid!'));
</script>
```
### Input Types
Some input types will automatically trigger constraints, such as `email` and `url`.
```html preview
<sl-form class="input-validation-type">
<sl-input type="email" label="Email" placeholder="you@example.com" required></sl-input>
<br>
<sl-input type="url" label="URL" placeholder="https://example.com/" required></sl-input>
<br>
<sl-button type="primary" submit>Submit</sl-button>
</sl-form>
<script>
const form = document.querySelector('.input-validation-type');
form.addEventListener('sl-submit', () => alert('All fields are valid!'));
</script>
```
### Custom Validation
To create a custom validation error, use the `setCustomValidity` method. The form will not be submitted when this method is called with anything other than an empty string, and its message will be shown by the browser as the validation error. To make the input valid again, call the method a second time with an empty string as the argument.
```html preview
<sl-form class="input-validation-custom">
<sl-input label="Type 'shoelace'" required></sl-input>
<br>
<sl-button type="primary" submit>Submit</sl-button>
</sl-form>
<script>
const form = document.querySelector('.input-validation-custom');
const input = form.querySelector('sl-input');
form.addEventListener('sl-submit', () => alert('All fields are valid!'));
input.addEventListener('sl-input', () => {
if (input.value === 'shoelace') {
input.setCustomValidity('');
} else {
input.setCustomValidity('Hey, you\'re supposed to type \'shoelace\' before submitting this!');
}
});
</script>
```
### Custom Validation Styles
The `invalid` attribute reflects the form control's validity, so you can style invalid fields using the `[invalid]` selector. The example below demonstrates how you can give erroneous fields a different appearance. Type something other than "shoelace" to demonstrate this.
```html preview
<sl-input class="custom-input" required pattern="shoelace">
<small slot="help-text">Please enter "shoelace" to continue</small>
</sl-input>
<style>
.custom-input[invalid]:not([disabled])::part(label),
.custom-input[invalid]:not([disabled])::part(help-text) {
color: rgb(var(--sl-color-danger-600));
}
.custom-input[invalid]:not([disabled])::part(base) {
border-color: rgb(var(--sl-color-danger-500));
}
.custom-input[invalid]:focus-within::part(base) {
box-shadow: 0 0 0 var(--sl-focus-ring-width) rgb(var(--sl-color-danger-500) / var(--sl-focus-ring-alpha));
}
</style>
```
### Third-party Validation
To opt out of the browser's built-in validation and use your own, add the `novalidate` attribute to the form. This will ignore all constraints and prevent the browser from showing its own warnings when form controls are invalid.
Remember that the `invalid` attribute on form controls reflects validity as defined by the [Constraint Validation API](https://developer.mozilla.org/en-US/docs/Web/Guide/HTML/HTML5/Constraint_validation). You can set it initially, but the `invalid` attribute will update as the user interacts with the form control. As such, you should not rely on it to set invalid styles using a custom validation library.
Instead, toggle a class and target it in your stylesheet as shown below.
```html
<sl-form novalidate>
<sl-input class="invalid"></sl-input>
</sl-form>
<style>
sl-input.invalid {
...
}
</style>
```
[component-metadata:sl-form]

View File

@@ -1,58 +0,0 @@
# Format Bytes
[component-header:sl-format-bytes]
Formats a number as a human readable bytes value.
```html preview
<div class="format-bytes-overview">
The file is <sl-format-bytes value="1000"></sl-format-bytes> in size.
<br><br>
<sl-input type="number" value="1000" label="Number to Format" style="max-width: 180px;"></sl-input>
</div>
<script>
const container = document.querySelector('.format-bytes-overview');
const formatter = container.querySelector('sl-format-bytes');
const input = container.querySelector('sl-input');
input.addEventListener('sl-input', () => formatter.value = input.value || 0);
</script>
```
## Examples
### Formatting Bytes
Set the `value` attribute to a number to get the value in bytes.
```html preview
<sl-format-bytes value="12"></sl-format-bytes><br>
<sl-format-bytes value="1200"></sl-format-bytes><br>
<sl-format-bytes value="1200000"></sl-format-bytes><br>
<sl-format-bytes value="1200000000"></sl-format-bytes>
```
### Formatting Bits
To get the value in bits, set the `unit` attribute to `bits`.
```html preview
<sl-format-bytes value="12" unit="bits"></sl-format-bytes><br>
<sl-format-bytes value="1200" unit="bits"></sl-format-bytes><br>
<sl-format-bytes value="1200000" unit="bits"></sl-format-bytes><br>
<sl-format-bytes value="1200000000" unit="bits"></sl-format-bytes>
```
### Localization
Use the `locale` attribute to set the number formatting locale.
```html preview
<sl-format-bytes value="12" locale="de"></sl-format-bytes><br>
<sl-format-bytes value="1200" locale="de"></sl-format-bytes><br>
<sl-format-bytes value="1200000" locale="de"></sl-format-bytes><br>
<sl-format-bytes value="1200000000" locale="de"></sl-format-bytes>
```
[component-metadata:sl-format-bytes]

View File

@@ -1,64 +0,0 @@
# Format Date
[component-header:sl-format-date]
Formats a date/time using the specified locale and options.
Localization is handled by the browser's [`Intl.DateTimeFormat` API](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/DateTimeFormat). No language packs are required.
```html preview
<!-- Shoelace 2 release date 🎉 -->
<sl-format-date date="2020-07-15T09:17:00-04:00"></sl-format-date>
```
The `date` attribute determines the date/time to use when formatting. It must be a string that [`Date.parse()`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/parse) can interpret or a [`Date`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date) object set via JavaScript. If omitted, the current date/time will be assumed.
?> When using strings, avoid ambiguous dates such as `03/04/2020` which can be interpreted as March 4 or April 3 depending on the user's browser and locale. Instead, always use a valid [ISO 8601 date time string](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/parse#Date_Time_String_Format) to ensure the date will be parsed properly by all clients.
## Examples
### Date & Time Formatting
Formatting options are based on those found in the [`Intl.DateTimeFormat` API](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/DateTimeFormat). When formatting options are provided, the date/time will be formatted according to those values. When no formatting options are provided, a localized, numeric date will be displayed instead.
```html preview
<!-- Human-readable date -->
<sl-format-date month="long" day="numeric" year="numeric"></sl-format-date><br>
<!-- Time -->
<sl-format-date hour="numeric" minute="numeric"></sl-format-date><br>
<!-- Weekday -->
<sl-format-date weekday="long"></sl-format-date><br>
<!-- Month -->
<sl-format-date month="long"></sl-format-date><br>
<!-- Year -->
<sl-format-date year="numeric"></sl-format-date><br>
<!-- No formatting options -->
<sl-format-date></sl-format-date>
```
### Hour Formatting
By default, the browser will determine whether to use 12-hour or 24-hour time. To force one or the other, set the `hour-format` attribute to `12` or `24`.
```html preview
<sl-format-date hour="numeric" minute="numeric" hour-format="12"></sl-format-date><br>
<sl-format-date hour="numeric" minute="numeric" hour-format="24"></sl-format-date>
```
### Localization
Use the `locale` attribute to set the date/time formatting locale.
```html preview
English: <sl-format-date locale="en"></sl-format-date><br>
French: <sl-format-date locale="fr"></sl-format-date><br>
Russian: <sl-format-date locale="ru"></sl-format-date><br>
```
[component-metadata:sl-format-date]

View File

@@ -1,61 +0,0 @@
# Format Number
[component-header:sl-format-number]
Formats a number using the specified locale and options.
Localization is handled by the browser's [`Intl.NumberFormat` API](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/NumberFormat/NumberFormat). No language packs are required.
```html preview
<div class="format-number-overview">
<sl-format-number value="1000"></sl-format-number>
<br><br>
<sl-input type="number" value="1000" label="Number to Format" style="max-width: 180px;"></sl-input>
</div>
<script>
const container = document.querySelector('.format-number-overview');
const formatter = container.querySelector('sl-format-number');
const input = container.querySelector('sl-input');
input.addEventListener('sl-input', () => formatter.value = input.value || 0);
</script>
```
## Examples
### Percentages
To get the value as a percent, set the `type` attribute to `percent`.
```html preview
<sl-format-number type="percent" value="0"></sl-format-number><br>
<sl-format-number type="percent" value=".25"></sl-format-number><br>
<sl-format-number type="percent" value=".50"></sl-format-number><br>
<sl-format-number type="percent" value=".75"></sl-format-number><br>
<sl-format-number type="percent" value="1"></sl-format-number>
```
### Localization
Use the `locale` attribute to set the number formatting locale.
```html preview
English: <sl-format-number value="2000" locale="en" minimum-fraction-digits="2"></sl-format-number><br>
German: <sl-format-number value="2000" locale="de" minimum-fraction-digits="2"></sl-format-number><br>
Russian: <sl-format-number value="2000" locale="ru" minimum-fraction-digits="2"></sl-format-number>
```
### Currency
To format a number as a monetary value, set the `type` attribute to `currency` and set the `currency` attribute to the desired ISO 4217 currency code. You should also specify `locale` to ensure the the number is formatted correctly for the target locale.
```html preview
<sl-format-number type="currency" currency="USD" value="2000" locale="en-US"></sl-format-number><br>
<sl-format-number type="currency" currency="GBP" value="2000" locale="en-GB"></sl-format-number><br>
<sl-format-number type="currency" currency="EUR" value="2000" locale="de"></sl-format-number><br>
<sl-format-number type="currency" currency="RUB" value="2000" locale="ru"></sl-format-number><br>
<sl-format-number type="currency" currency="CNY" value="2000" locale="zh-cn"></sl-format-number>
```
[component-metadata:sl-format-number]

View File

@@ -1,78 +0,0 @@
# Icon Button
[component-header:sl-icon-button]
Icons buttons are simple, icon-only buttons that can be used for actions and in toolbars.
For a full list of icons that come bundled with Shoelace, refer to the [icon component](/components/icon).
```html preview
<sl-icon-button name="gear" label="Settings"></sl-icon-button>
```
## Examples
### Sizes
Icon buttons inherit their parent element's `font-size`.
```html preview
<sl-icon-button name="pencil" label="Edit" style="font-size: 1.5rem;"></sl-icon-button>
<sl-icon-button name="pencil" label="Edit" style="font-size: 2rem;"></sl-icon-button>
<sl-icon-button name="pencil" label="Edit" style="font-size: 2.5rem;"></sl-icon-button>
```
### Colors
Icon buttons are designed to have a uniform appearance, so their color is not inherited. However, you can still customize them by styling the `base` part.
```html preview
<div class="icon-button-color">
<sl-icon-button name="type-bold" label="Bold"></sl-icon-button>
<sl-icon-button name="type-italic" label="Italic"></sl-icon-button>
<sl-icon-button name="type-underline" label="Underline"></sl-icon-button>
</div>
<style>
.icon-button-color sl-icon-button::part(base) {
color: #b00091;
}
.icon-button-color sl-icon-button::part(base):hover,
.icon-button-color sl-icon-button::part(base):focus {
color: #c913aa;
}
.icon-button-color sl-icon-button::part(base):active {
color: #960077;
}
</style>
```
### Link Buttons
Use the `href` attribute to convert the button to a link.
```html preview
<sl-icon-button name="gear" label="Settings" href="https://example.com" target="_blank"></sl-icon-button>
```
### Icon Button with Tooltip
Wrap a tooltip around an icon button to provide contextual information to the user.
```html preview
<sl-tooltip content="Settings">
<sl-icon-button name="gear" label="Settings"></sl-icon-button>
</sl-tooltip>
```
### Disabled
Use the `disabled` attribute to disable the icon button.
```html preview
<sl-icon-button name="gear" label="Settings" disabled></sl-icon-button>
```
[component-metadata:sl-icon-button]

View File

@@ -1,29 +0,0 @@
# Image Comparer
[component-header:sl-image-comparer]
Compare visual differences between similar photos with a sliding panel.
For best results, use images that share the same dimensions. The slider can be controlled by dragging or pressing the left and right arrow keys. (Tip: press shift + arrows to move the slider in larger intervals, or home + end to jump to the beginning or end.)
```html preview
<sl-image-comparer>
<img slot="before" src="https://images.unsplash.com/photo-1517331156700-3c241d2b4d83?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=800&q=80&sat=-100&bri=-5" alt="Grayscale version of kittens in a basket looking around.">
<img slot="after" src="https://images.unsplash.com/photo-1517331156700-3c241d2b4d83?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=800&q=80" alt="Color version of kittens in a basket looking around.">
</sl-image-comparer>
```
## Examples
### Initial Position
Use the `position` attribute to set the initial position of the slider. This is a percentage from `0` to `100`.
```html preview
<sl-image-comparer position="25">
<img slot="before" src="https://images.unsplash.com/photo-1520903074185-8eca362b3dce?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1200&q=80" alt="A person sitting on bricks wearing untied boots.">
<img slot="after" src="https://images.unsplash.com/photo-1520640023173-50a135e35804?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=2250&q=80" alt="A person sitting on a yellow curb tying shoelaces on a boot.">
</sl-image-comparer>
```
[component-metadata:sl-image-comparer]

View File

@@ -1,141 +0,0 @@
# Input
[component-header:sl-input]
Inputs collect data from the user.
```html preview
<sl-input></sl-input>
```
?> This component doesn't work with standard forms. Use [`<sl-form>`](/components/form) instead.
?> Please refer to the section on [form control validation](/components/form?id=form-control-validation) to learn how to do client-side validation.
## Examples
### Placeholders
Use the `placeholder` attribute to add a placeholder.
```html preview
<sl-input placeholder="Type something"></sl-input>
```
### Clearable
Add the `clearable` attribute to add a clear button when the input has content.
```html preview
<sl-input placeholder="Clearable" clearable></sl-input>
```
### Toggle Password
Add the `toggle-password` attribute to add a toggle button that will show the password when activated.
```html preview
<sl-input type="password" placeholder="Password Toggle" size="small" toggle-password></sl-input>
<br>
<sl-input type="password" placeholder="Password Toggle" size="medium" toggle-password></sl-input>
<br>
<sl-input type="password" placeholder="Password Toggle" size="large" toggle-password></sl-input>
```
### Filled Inputs
Add the `filled` attribute to draw a filled input.
```html preview
<sl-input placeholder="Type something" filled></sl-input>
```
### Pill
Use the `pill` attribute to give inputs rounded edges.
```html preview
<sl-input placeholder="Small" size="small" pill></sl-input>
<br>
<sl-input placeholder="Medium" size="medium" pill></sl-input>
<br>
<sl-input placeholder="Large" size="large" pill></sl-input>
```
### Input Types
The `type` attribute controls the type of input the browser renders.
```html preview
<sl-input type="email" Placeholder="Email"></sl-input>
<br>
<sl-input type="number" Placeholder="Number"></sl-input>
<br>
<sl-input type="date" Placeholder="Date"></sl-input>
```
### Disabled
Use the `disabled` attribute to disable an input.
```html preview
<sl-input placeholder="Disabled" size="small" disabled></sl-input>
<br>
<sl-input placeholder="Disabled" size="medium" disabled></sl-input>
<br>
<sl-input placeholder="Disabled" size="large" disabled></sl-input>
```
### Sizes
Use the `size` attribute to change an input's size.
```html preview
<sl-input placeholder="Small" size="small"></sl-input>
<br>
<sl-input placeholder="Medium" size="medium"></sl-input>
<br>
<sl-input placeholder="Large" size="large"></sl-input>
```
### Prefix & Suffix Icons
Use the `prefix` and `suffix` slots to add icons.
```html preview
<sl-input placeholder="Small" size="small">
<sl-icon name="house" slot="prefix"></sl-icon>
<sl-icon name="chat" slot="suffix"></sl-icon>
</sl-input>
<br>
<sl-input placeholder="Medium" size="medium">
<sl-icon name="house" slot="prefix"></sl-icon>
<sl-icon name="chat" slot="suffix"></sl-icon>
</sl-input>
<br>
<sl-input placeholder="Large" size="large">
<sl-icon name="house" slot="prefix"></sl-icon>
<sl-icon name="chat" slot="suffix"></sl-icon>
</sl-input>
```
### Labels
Use the `label` attribute to give the input an accessible label. For labels that contain HTML, use the `label` slot instead.
```html preview
<sl-input label="What is your name?"></sl-input>
```
### Help Text
Add descriptive help text to an input with the `help-text` attribute. For help texts that contain HTML, use the `help-text` slot instead.
```html preview
<sl-input
label="Nickname"
help-text="What would you like people to call you?"
></sl-input>
```
[component-metadata:sl-input]

View File

@@ -1,105 +0,0 @@
# Menu Item
[component-header:sl-menu-item]
Menu items provide options for the user to pick from in a menu.
```html preview
<sl-menu style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item>Option 1</sl-menu-item>
<sl-menu-item>Option 2</sl-menu-item>
<sl-menu-item>Option 3</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item checked>Checked</sl-menu-item>
<sl-menu-item disabled>Disabled</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item>
Prefix Icon
<sl-icon slot="prefix" name="gift"></sl-icon>
</sl-menu-item>
<sl-menu-item>
Suffix Icon
<sl-icon slot="suffix" name="heart"></sl-icon>
</sl-menu-item>
</sl-menu>
```
## Examples
### Checked
Use the `checked` attribute to draw menu items in a checked state.
```html preview
<sl-menu style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item>Option 1</sl-menu-item>
<sl-menu-item checked>Option 2</sl-menu-item>
<sl-menu-item>Option 3</sl-menu-item>
</sl-menu>
```
### Disabled
Add the `disabled` attribute to disable the menu item so it cannot be selected.
```html preview
<sl-menu style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item>Option 1</sl-menu-item>
<sl-menu-item disabled>Option 2</sl-menu-item>
<sl-menu-item>Option 3</sl-menu-item>
</sl-menu>
```
### Prefix & Suffix
Add content to the start and end of menu items using the `prefix` and `suffix` slots.
```html preview
<sl-menu style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item>
<sl-icon slot="prefix" name="house"></sl-icon>
Home
</sl-menu-item>
<sl-menu-item>
<sl-icon slot="prefix" name="envelope"></sl-icon>
Messages
<sl-badge slot="suffix" type="primary" pill>12</sl-badge>
</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item>
<sl-icon slot="prefix" name="gear"></sl-icon>
Settings
</sl-menu-item>
</sl-menu>
```
### Value & Selection
The `value` attribute can be used to assign a hidden value, such as a unique identifier, to a menu item. When an item is selected, the `sl-select` event will be emitted and a reference to the item will be available at `event.detail.item`. You can use this reference to access the selected item's value, its checked state, and more.
```html preview
<sl-menu class="menu-value" style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item value="opt-1">Option 1</sl-menu-item>
<sl-menu-item value="opt-2">Option 2</sl-menu-item>
<sl-menu-item value="opt-3">Option 3</sl-menu-item>
</sl-menu>
<script>
const menu = document.querySelector('.menu-value');
menu.addEventListener('sl-select', event => {
const item = event.detail.item;
// Toggle checked state
item.checked = !item.checked;
// Log value
console.log(`Selected value: ${item.value}`);
});
</script>
```
[component-metadata:sl-menu-item]

View File

@@ -1,23 +0,0 @@
# Menu Label
[component-header:sl-menu-label]
Menu labels are used to describe a group of menu items.
```html preview
<sl-menu
style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);"
>
<sl-menu-label>Fruits</sl-menu-label>
<sl-menu-item value="apple">Apple</sl-menu-item>
<sl-menu-item value="banana">Banana</sl-menu-item>
<sl-menu-item value="orange">Orange</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-label>Vegetables</sl-menu-label>
<sl-menu-item value="broccoli">Broccoli</sl-menu-item>
<sl-menu-item value="carrot">Carrot</sl-menu-item>
<sl-menu-item value="zucchini">Zucchini</sl-menu-item>
</sl-menu>
```
[component-metadata:sl-menu-label]

View File

@@ -1,23 +0,0 @@
# Menu
[component-header:sl-menu]
Menus provide a list of options for the user to choose from.
You can use [menu items](/components/menu-item), [menu labels](/components/menu-label), and [dividers](/components/divider) to compose a menu. Menus support keyboard interactions, including type-to-select an option.
```html preview
<sl-menu style="max-width: 200px; border: solid 1px rgb(var(--sl-panel-border-color)); border-radius: var(--sl-border-radius-medium);">
<sl-menu-item value="undo">Undo</sl-menu-item>
<sl-menu-item value="redo">Redo</sl-menu-item>
<sl-divider></sl-divider>
<sl-menu-item value="cut">Cut</sl-menu-item>
<sl-menu-item value="copy">Copy</sl-menu-item>
<sl-menu-item value="paste">Paste</sl-menu-item>
<sl-menu-item value="delete">Delete</sl-menu-item>
</sl-menu>
```
?> Menus are intended for system menus (dropdown menus, select menus, context menus, etc.). They should not be mistaken for navigation menus which serve a different purpose and have a different semantic meaning. If you're building navigation, use `<nav>` and `<a>` elements instead.
[component-metadata:sl-menu]

View File

@@ -1,104 +0,0 @@
# Mutation Observer
[component-header:sl-mutation-observer]
The Mutation Observer component offers a thin, declarative interface to the [`MutationObserver API`](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver).
The mutation observer will report changes to the content it wraps through the `sl-mutation` event. When emitted, a collection of [MutationRecord](https://developer.mozilla.org/en-US/docs/Web/API/MutationRecord) objects will be attached to `event.detail` that contains information about how it changed.
```html preview
<div class="mutation-overview">
<sl-mutation-observer attr>
<sl-button type="primary">Click to mutate</sl-button>
</sl-mutation-observer>
<br>
👆 Click the button and watch the console
<script>
const container = document.querySelector('.mutation-overview');
const mutationObserver = container.querySelector('sl-mutation-observer');
const button = container.querySelector('sl-button');
const types = ['primary', 'success', 'neutral', 'warning', 'danger'];
let clicks = 0;
// Change the button's type attribute
button.addEventListener('click', () => {
clicks++;
button.setAttribute('type', types[clicks % types.length]);
});
// Log mutations
mutationObserver.addEventListener('sl-mutation', event => {
console.log(event.detail);
});
</script>
<style>
.mutation-overview sl-button {
margin-bottom: 1rem;
}
</style>
</div>
```
?> When you create a mutation observer, you must indicate what changes it should respond to by including at least one of `attr`, `child-list`, or `char-data`. If you don't specify at least one of these attributes, no mutation events will be emitted.
## Examples
### Child List
Use the `child-list` attribute to watch for new child elements that are added or removed.
```html preview
<div class="mutation-child-list">
<sl-mutation-observer child-list>
<div class="buttons">
<sl-button type="primary">Add button</sl-button>
</div>
</sl-mutation-observer>
👆 Add and remove buttons and watch the console
<script>
const container = document.querySelector('.mutation-child-list');
const mutationObserver = container.querySelector('sl-mutation-observer');
const buttons = container.querySelector('.buttons');
const button = container.querySelector('sl-button[type="primary"]');
let i = 0;
// Add a button
button.addEventListener('click', () => {
const button = document.createElement('sl-button');
button.textContent = ++i;
buttons.append(button);
});
// Remove a button
buttons.addEventListener('click', event => {
const target = event.target.closest('sl-button:not([type="primary"])');
event.stopPropagation();
if (target) {
target.remove();
}
});
// Log mutations
mutationObserver.addEventListener('sl-mutation', event => {
console.log(event.detail);
});
</script>
<style>
.mutation-child-list .buttons {
display: flex;
gap: .25rem;
flex-wrap: wrap;
margin-bottom: 1rem;
}
</style>
</div>
```
[component-metadata:sl-mutation-observer]

View File

@@ -1,68 +0,0 @@
# Progress Bar
[component-header:sl-progress-bar]
Progress bars are used to show the status of an ongoing operation.
```html preview
<sl-progress-bar value="50"></sl-progress-bar>
```
## Examples
### Custom Height
Use the `--height` custom property to set the progress bar's height.
```html preview
<sl-progress-bar value="50" style="--height: 6px;"></sl-progress-bar>
```
### Labels
Use the `label` attribute to label the progress bar and tell assistive devices how to announce it.
```html preview
<sl-progress-bar value="50" label="Upload progress"></sl-progress-bar>
```
### Showing Values
Use the default slot to show a value.
```html preview
<sl-progress-bar value="50" class="progress-bar-values">50%</sl-progress-bar>
<br>
<sl-button circle><sl-icon name="dash"></sl-icon></sl-button>
<sl-button circle><sl-icon name="plus"></sl-icon></sl-button>
<script>
const progressBar = document.querySelector('.progress-bar-values');
const subtractButton = progressBar.nextElementSibling.nextElementSibling;
const addButton = subtractButton.nextElementSibling;
addButton.addEventListener('click', () => {
const value = Math.min(100, progressBar.value + 10);
progressBar.value = value;
progressBar.textContent = `${value}%`;
});
subtractButton.addEventListener('click', () => {
const value = Math.max(0, progressBar.value - 10)
progressBar.value = value;
progressBar.textContent = `${value}%`;
});
</script>
```
### Indeterminate
The `indeterminate` attribute can be used to inform the user that the operation is pending, but its status cannot currently be determined. In this state, `value` is ignored and the label, if present, will not be shown.
```html preview
<sl-progress-bar indeterminate></sl-progress-bar>
```
[component-metadata:sl-progress-bar]

View File

@@ -1,82 +0,0 @@
# Progress Ring
[component-header:sl-progress-ring]
Progress rings are used to show the progress of a determinate operation in a circular fashion.
```html preview
<sl-progress-ring value="25"></sl-progress-ring>
```
## Examples
### Size
Use the `--size` custom property to set the diameter of the progress ring.
```html preview
<sl-progress-ring value="50" style="--size: 200px;"></sl-progress-ring>
```
### Track Width
Use the `--track-width` custom property to set the width of the progress ring's track.
```html preview
<sl-progress-ring value="50" style="--track-width: 10px;"></sl-progress-ring>
```
### Colors
To change the color, use the `--track-color` and `--indicator-color` custom properties.
```html preview
<sl-progress-ring
value="50"
style="
--track-color: pink;
--indicator-color: deeppink;
"
></sl-progress-ring>
```
### Labels
Use the `label` attribute to label the progress ring and tell assistive devices how to announce it.
```html preview
<sl-progress-ring value="50" label="Upload progress"></sl-progress-ring>
```
### Showing Values
Use the default slot to show a label.
```html preview
<sl-progress-ring value="50" class="progress-ring-values" style="margin-bottom: .5rem;">50%</sl-progress-ring>
<br>
<sl-button circle><sl-icon name="dash"></sl-icon></sl-button>
<sl-button circle><sl-icon name="plus"></sl-icon></sl-button>
<script>
const progressRing = document.querySelector('.progress-ring-values');
const subtractButton = progressRing.nextElementSibling.nextElementSibling;
const addButton = subtractButton.nextElementSibling;
addButton.addEventListener('click', () => {
const value = Math.min(100, progressRing.value + 10);
progressRing.value = value;
progressRing.textContent = `${value}%`;
});
subtractButton.addEventListener('click', () => {
const value = Math.max(0, progressRing.value - 10)
progressRing.value = value;
progressRing.textContent = `${value}%`;
});
</script>
```
[component-metadata:sl-progress-ring]

View File

@@ -1,84 +0,0 @@
# QR Code
[component-header:sl-qr-code]
Generates a [QR code](https://www.qrcode.com/) and renders it using the [Canvas API](https://developer.mozilla.org/en-US/docs/Web/API/Canvas_API).
QR codes are useful for providing small pieces of information to users who can quickly scan them with a smartphone. Most smartphones have built-in QR code scanners, so simply pointing the camera at a QR code will decode it and allow the user to visit a website, dial a phone number, read a message, etc.
```html preview
<div class="qr-overview">
<sl-qr-code value="https://shoelace.style/" label="Scan this code to visit Shoelace on the web!"></sl-qr-code>
<br>
<sl-input maxlength="255" clearable></sl-input>
</div>
<script>
const container = document.querySelector('.qr-overview');
const qrCode = container.querySelector('sl-qr-code');
const input = container.querySelector('sl-input');
input.value = qrCode.value;
input.addEventListener('sl-input', () => qrCode.value = input.value);
</script>
<style>
.qr-overview {
max-width: 256px;
}
.qr-overview sl-input {
margin-top: 1rem;
}
</style>
```
## Examples
### Colors
Use the `fill` and `background` attributes to modify the QR code's colors. You should always ensure good contrast for optimal compatibility with QR code scanners.
```html preview
<sl-qr-code value="https://shoelace.style/" fill="deeppink" background="white"></sl-qr-code>
```
### Size
Use the `size` attribute to change the size of the QR code.
```html preview
<sl-qr-code value="https://shoelace.style/" size="64"></sl-qr-code>
```
### Radius
Create a rounded effect with the `radius` attribute.
```html preview
<sl-qr-code value="https://shoelace.style/" radius="0.5"></sl-qr-code>
```
### Error Correction
QR codes can be rendered with various levels of [error correction](https://www.qrcode.com/en/about/error_correction.html) that can be set using the `error-correction` attribute. This example generates four codes with the same value using different error correction levels.
```html preview
<div class="qr-error-correction">
<sl-qr-code value="https://shoelace.style/" error-correction="L"></sl-qr-code>
<sl-qr-code value="https://shoelace.style/" error-correction="M"></sl-qr-code>
<sl-qr-code value="https://shoelace.style/" error-correction="Q"></sl-qr-code>
<sl-qr-code value="https://shoelace.style/" error-correction="H"></sl-qr-code>
</div>
<style>
.qr-error-correction {
display: flex;
flex-wrap: wrap;
gap: 1rem;
}
</style>
```
[component-metadata:sl-qr-code]

View File

@@ -1,29 +0,0 @@
# Radio Group
[component-header:sl-radio-group]
Radio Groups are used to group multiple radios so they function as a single control.
```html preview
<sl-radio-group label="Select an item">
<sl-radio value="1" checked>Item 1</sl-radio>
<sl-radio value="2">Item 2</sl-radio>
<sl-radio value="3">Item 3</sl-radio>
</sl-radio-group>
```
## Examples
### Showing the Fieldset
You can show a fieldset and legend that wraps the radio group using the `fieldset` attribute.
```html preview
<sl-radio-group label="Select an item" fieldset>
<sl-radio value="1" checked>Item 1</sl-radio>
<sl-radio value="2">Item 2</sl-radio>
<sl-radio value="3">Item 3</sl-radio>
</sl-radio-group>
```
[component-metadata:sl-radio-group]

View File

@@ -1,34 +0,0 @@
# Radio
[component-header:sl-radio]
Radios allow the user to select one option from a group of many.
Radios are designed to be used with [radio groups](/components/radio-group). As such, all of the examples on this page utilize them to demonstrate their correct usage.
```html preview
<sl-radio-group label="Select an option" no-fieldset>
<sl-radio value="1" checked>Option 1</sl-radio>
<sl-radio value="2">Option 2</sl-radio>
<sl-radio value="3">Option 3</sl-radio>
</sl-radio-group>
```
?> This component doesn't work with standard forms. Use [`<sl-form>`](/components/form) instead.
## Examples
### Disabled
Use the `disabled` attribute to disable a radio.
```html preview
<sl-radio-group label="Select an option" no-fieldset>
<sl-radio value="1" checked>Option 1</sl-radio>
<sl-radio value="2">Option 2</sl-radio>
<sl-radio value="3">Option 3</sl-radio>
<sl-radio value="4" disabled>Disabled</sl-radio>
</sl-radio-group>
```
[component-metadata:sl-radio]

View File

@@ -1,84 +0,0 @@
# Range
[component-header:sl-range]
Ranges allow the user to select a single value within a given range using a slider.
```html preview
<sl-range></sl-range>
```
?> This component doesn't work with standard forms. Use [`<sl-form>`](/components/form) instead.
## Examples
### Disabled
Use the `disabled` attribute to disable a slider.
```html preview
<sl-range min="0" max="100" step="1" disabled></sl-range>
```
### Tooltip Placement
By default, the tooltip is shown on top. Set `tooltip` to `bottom` to show it below the slider.
```html preview
<sl-range min="0" max="100" step="1" tooltip="bottom"></sl-range>
```
### Disable the Tooltip
To disable the tooltip, set `tooltip` to `none`.
```html preview
<sl-range min="0" max="100" step="1" tooltip="none"></sl-range>
```
### Custom Track Colors
You can customize the active and inactive portions of the track using the `--track-color-active` and `--track-color-inactive` custom properties.
```html preview
<sl-range style="
--track-color-active: rgb(var(--sl-color-primary-600));
--track-color-inactive: rgb(var(--sl-color-primary-200));
"></sl-range>
```
### Custom Tooltip Formatter
You can change the tooltip's content by setting the `tooltipFormatter` property to a function that accepts the range's value as an argument.
```html preview
<sl-range min="0" max="100" step="1" class="range-with-custom-formatter"></sl-range>
<script>
const range = document.querySelector('.range-with-custom-formatter');
range.tooltipFormatter = value => `Total - ${value}%`;
</script>
```
### Labels
Use the `label` attribute to give the range an accessible label. For labels that contain HTML, use the `label` slot instead.
```html preview
<sl-range label="Volume" min="0" max="100"></sl-input>
```
### Help Text
Add descriptive help text to a range with the `help-text` attribute. For help texts that contain HTML, use the `help-text` slot instead.
```html preview
<sl-range
label="Volume"
help-text="Controls the volume of the current song."
min="0"
max="100"
></sl-input>
```
[component-metadata:sl-range]

View File

@@ -1,79 +0,0 @@
# Rating
[component-header:sl-rating]
Ratings give users a way to quickly view and provide feedback.
```html preview
<sl-rating></sl-rating>
```
## Examples
### Maximum Value
Ratings are 0-5 by default. To change the maximum possible value, use the `max` attribute.
```html preview
<sl-rating max="3"></sl-rating>
```
### Precision
Use the `precision` attribute to let users select fractional ratings.
```html preview
<sl-rating precision=".5" value="2.5"></sl-rating>
```
## Symbol Sizes
Set the `--symbol-size` custom property to adjust the size.
```html preview
<sl-rating style="--symbol-size: 2rem;"></sl-rating>
```
### Readonly
Use the `readonly` attribute to display a rating that users can't change.
```html preview
<sl-rating readonly value="3"></sl-rating>
```
### Disabled
Use the `disable` attribute to disable the rating.
```html preview
<sl-rating disabled value="3"></sl-rating>
```
### Custom Icons
```html preview
<sl-rating class="rating-hearts" style="--symbol-color-active: #ff4136;"></sl-rating>
<script>
const rating = document.querySelector('.rating-hearts');
rating.getSymbol = () => '<sl-icon name="heart-fill"></sl-icon>';
</script>
```
### Value-based Icons
```html preview
<sl-rating class="rating-emojis"></sl-rating>
<script>
const rating = document.querySelector('.rating-emojis');
rating.getSymbol = (value) => {
const icons = ['emoji-angry', 'emoji-frown', 'emoji-expressionless', 'emoji-smile', 'emoji-laughing'];
return `<sl-icon name="${icons[value - 1]}"></sl-icon>`;
};
</script>
```
[component-metadata:sl-rating]

View File

@@ -1,61 +0,0 @@
# Relative Time
[component-header:sl-relative-time]
Outputs a localized time phrase relative to the current date and time.
Localization is handled by the browser's [`Intl.RelativeTimeFormat` API](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/RelativeTimeFormat). No language packs are required.
```html preview
<!-- Shoelace 2 release date 🎉 -->
<sl-relative-time date="2020-07-15T09:17:00-04:00"></sl-relative-time>
```
The `date` attribute determines when the date/time is calculated from. It must be a string that [`Date.parse()`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/parse) can interpret or a [`Date`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date) object set via JavaScript.
?> When using strings, avoid ambiguous dates such as `03/04/2020` which can be interpreted as March 4 or April 3 depending on the user's browser and locale. Instead, always use a valid [ISO 8601 date time string](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/parse#Date_Time_String_Format) to ensure the date will be parsed properly by all clients.
!> The `Intl.RelativeTimeFormat` API is available [in all major browsers](https://caniuse.com/mdn-javascript_builtins_intl_relativetimeformat), but it only became available to Safari in version 14. If you need to support Safari 13, you'll need to [use a polyfill](https://github.com/catamphetamine/relative-time-format).
## Examples
### Keeping Time in Sync
Use the `sync` attribute to update the displayed value automatically as time passes.
```html preview
<div class="relative-time-sync">
<sl-relative-time sync></sl-relative-time>
</div>
<script>
const container = document.querySelector('.relative-time-sync');
const relativeTime = container.querySelector('sl-relative-time');
relativeTime.date = new Date(new Date().getTime() - 60000);
</script>
```
### Formatting Styles
You can change how the time is displayed using the `format` attribute. Note that some locales may display the same values for `narrow` and `short` formats.
```html preview
<sl-relative-time date="2020-07-15T09:17:00-04:00" format="narrow"></sl-relative-time><br>
<sl-relative-time date="2020-07-15T09:17:00-04:00" format="short"></sl-relative-time><br>
<sl-relative-time date="2020-07-15T09:17:00-04:00" format="long"></sl-relative-time>
```
### Localization
Use the `locale` attribute to set the desired locale.
```html preview
English: <sl-relative-time date="2020-07-15T09:17:00-04:00" locale="en-US"></sl-relative-time><br>
Chinese: <sl-relative-time date="2020-07-15T09:17:00-04:00" locale="zh-CN"></sl-relative-time><br>
German: <sl-relative-time date="2020-07-15T09:17:00-04:00" locale="de"></sl-relative-time><br>
Greek: <sl-relative-time date="2020-07-15T09:17:00-04:00" locale="el"></sl-relative-time><br>
Russian: <sl-relative-time date="2020-07-15T09:17:00-04:00" locale="ru"></sl-relative-time>
```
[component-metadata:sl-relative-time]

Some files were not shown because too many files have changed in this diff Show More