Use svelte-inline-compile library to add more unit tests (mostly slot prop)

This brings the number of tests from 381 => 424 which I'm pleased with.

It'd be nice to replace my TestRenderer tests with this but it's not worth the effort.
This commit is contained in:
Ryan Gossiaux
2021-12-30 15:43:39 -10:00
parent 72b0b838e4
commit 3ff520d72d
8 changed files with 1223 additions and 1500 deletions

View File

@@ -14,6 +14,8 @@ import {
assertActiveElement,
assertDialog,
assertDialogDescription,
assertDialogOverlay,
assertDialogTitle,
DialogState,
getByText,
getDialog,
@@ -24,6 +26,7 @@ import {
import { click, Keys, press } from "$lib/test-utils/interactions";
import Transition from "$lib/components/transitions/TransitionRoot.svelte";
import { tick } from "svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock("../../hooks/use-id", () => {
@@ -105,41 +108,29 @@ describe("Rendering", () => {
})
);
// TODO: render prop tests!
it(
'Dialog should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<script>
let isOpen = false;
</script>
<button id="trigger" on:click={() => isOpen = (true)}>
Trigger
</button>
<Dialog open={isOpen} on:close={(e) => isOpen = e.detail} let:open>
<pre>{JSON.stringify({open})}</pre>
<TestTabSentinel />
</Dialog>
`)
// it(
// 'should be possible to render a Dialog using a render prop',
// suppressConsoleLogs(async () => {
// function Example() {
// let [isOpen, setIsOpen] = useState(false)
assertDialog({ state: DialogState.InvisibleUnmounted })
// return (
// <>
// <button id= "trigger" onClick = {() => setIsOpen(true)
// }>
// Trigger
// < /button>
// < Dialog open = { isOpen } onClose = { setIsOpen } >
// { data => (
// <>
// <pre>{ JSON.stringify(data) } < /pre>
// < TabSentinel />
// </>
// )
// }
// </Dialog>
// < />
// )
// }
// render(<Example />)
await click(document.getElementById('trigger'))
// assertDialog({ state: DialogState.InvisibleUnmounted })
// await click(document.getElementById('trigger'))
// assertDialog({ state: DialogState.Visible, textContent: JSON.stringify({ open: true }) })
// })
// )
assertDialog({ state: DialogState.Visible, textContent: JSON.stringify({ open: true }) })
})
)
it('should be possible to always render the Dialog if we provide it a `static` prop (and enable focus trapping based on `open`)', async () => {
let focusCounter = jest.fn()
@@ -235,91 +226,85 @@ describe("Rendering", () => {
})
)
})
// TODO: more render prop tests!
describe('DialogOverlay', () => {
it(
'DialogOverlay should have slot props',
suppressConsoleLogs(async () => {
let overlay = jest.fn().mockReturnValue(null)
render(svelte`
<script>
let isOpen = false;
</script>
<button id="trigger" on:click={() => isOpen = !isOpen}>
Trigger
</button>
<Dialog open={isOpen} on:close={(e) => isOpen = e.detail}>
<DialogOverlay let:open>{overlay({ open })}</DialogOverlay>
<TestTabSentinel />
</Dialog>
`)
// describe('Dialog.Overlay', () => {
// it(
// 'should be possible to render Dialog.Overlay using a render prop',
// suppressConsoleLogs(async () => {
// let overlay = jest.fn().mockReturnValue(null)
// function Example() {
// let [isOpen, setIsOpen] = useState(false)
// return (
// <>
// <button id="trigger" onClick={() => setIsOpen(v => !v)}>
// Trigger
// </button>
// <Dialog open={isOpen} onClose={setIsOpen}>
// <Dialog.Overlay>{overlay}</Dialog.Overlay>
// <TabSentinel />
// </Dialog>
// </>
// )
// }
assertDialogOverlay({
state: DialogState.InvisibleUnmounted,
attributes: { id: 'headlessui-dialog-overlay-2' },
})
// render(<Example />)
await click(document.getElementById('trigger'))
// assertDialogOverlay({
// state: DialogState.InvisibleUnmounted,
// attributes: { id: 'headlessui-dialog-overlay-2' },
// })
assertDialogOverlay({
state: DialogState.Visible,
attributes: { id: 'headlessui-dialog-overlay-2' },
})
expect(overlay).toHaveBeenCalledWith({ open: true })
})
)
})
// await click(document.getElementById('trigger'))
describe('DialogTitle', () => {
it(
'DialogTitle should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Dialog open={true} on:close={console.log}>
<DialogTitle let:open>{JSON.stringify({ open })}</DialogTitle>
<TestTabSentinel />
</Dialog>
`)
// assertDialogOverlay({
// state: DialogState.Visible,
// attributes: { id: 'headlessui-dialog-overlay-2' },
// })
// expect(overlay).toHaveBeenCalledWith({ open: true })
// })
// )
// })
assertDialog({
state: DialogState.Visible,
attributes: { id: 'headlessui-dialog-1' },
})
assertDialogTitle({
state: DialogState.Visible,
textContent: JSON.stringify({ open: true }),
})
})
)
})
// describe('Dialog.Title', () => {
// it(
// 'should be possible to render Dialog.Title using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Dialog open={true} onClose={console.log}>
// <Dialog.Title>{JSON.stringify}</Dialog.Title>
// <TabSentinel />
// </Dialog>
// )
describe('DialogDescription', () => {
it(
'DialogDescription should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Dialog open={true} on:close={console.log}>
<DialogDescription let:open>{JSON.stringify({ open })}</DialogDescription>
<TestTabSentinel />
</Dialog>
`)
// assertDialog({
// state: DialogState.Visible,
// attributes: { id: 'headlessui-dialog-1' },
// })
// assertDialogTitle({
// state: DialogState.Visible,
// textContent: JSON.stringify({ open: true }),
// })
// })
// )
// })
// describe('Dialog.Description', () => {
// it(
// 'should be possible to render Dialog.Description using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Dialog open={true} onClose={console.log}>
// <Dialog.Description>{JSON.stringify}</Dialog.Description>
// <TabSentinel />
// </Dialog>
// )
// assertDialog({
// state: DialogState.Visible,
// attributes: { id: 'headlessui-dialog-1' },
// })
// assertDialogDescription({
// state: DialogState.Visible,
// textContent: JSON.stringify({ open: true }),
// })
// })
// )
// })
assertDialog({
state: DialogState.Visible,
attributes: { id: 'headlessui-dialog-1' },
})
assertDialogDescription({
state: DialogState.Visible,
textContent: JSON.stringify({ open: true }),
})
})
)
})
})
describe('Composition', () => {
@@ -469,7 +454,7 @@ describe('Keyboard interactions', () => {
describe('Mouse interactions', () => {
it(
'should be possible to close a Dialog using a click on the Dialog.Overlay',
'should be possible to close a Dialog using a click on the DialogOverlay',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -497,7 +482,7 @@ describe('Mouse interactions', () => {
)
it(
'should not close the Dialog when clicking on contents of the Dialog.Overlay',
'should not close the Dialog when clicking on contents of the DialogOverlay',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -588,7 +573,7 @@ describe('Mouse interactions', () => {
)
it(
'should stop propagating click events when clicking on the Dialog.Overlay',
'should stop propagating click events when clicking on the DialogOverlay',
suppressConsoleLogs(async () => {
let wrapperFn = jest.fn()
render(
@@ -610,7 +595,7 @@ describe('Mouse interactions', () => {
// Verify that the wrapper function has not been called yet
expect(wrapperFn).toHaveBeenCalledTimes(0)
// Click the Dialog.Overlay to close the Dialog
// Click the DialogOverlay to close the Dialog
await click(getDialogOverlay())
// Verify it is closed
@@ -688,7 +673,7 @@ describe('Nesting', () => {
strategy | action
${'with `Escape`'} | ${() => press(Keys.Escape)}
${'with `Outside Click`'} | ${() => click(document.body)}
${'with `Click on Dialog.Overlay`'} | ${() => click(getDialogOverlays().pop()!)}
${'with `Click on DialogOverlay`'} | ${() => click(getDialogOverlays().pop()!)}
`(
'should be possible to open nested Dialog components and close them $strategy',
async ({ action }) => {

View File

@@ -14,6 +14,7 @@ import {
import { click, Keys, MouseButton, press } from "$lib/test-utils/interactions";
import { Transition, TransitionChild } from "../transitions";
import TransitionDebug from "./_TransitionDebug.svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock("../../hooks/use-id", () => {
@@ -72,240 +73,178 @@ describe("Safe guards", () => {
});
describe("Rendering", () => {
// describe('Disclosure', () => {
// it(
// 'should be possible to render a Disclosure using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Disclosure>
// {({ open }) => (
// <>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>Panel is: {open ? 'open' : 'closed'}</DisclosurePanel>
// </>
// )}
// </Disclosure>
// )
describe('Disclosure', () => {
it(
'should render a Disclosure with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Disclosure let:open>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel>Panel is: {open ? 'open' : 'closed'}</DisclosurePanel>
</Disclosure>
`)
// assertDisclosureButton({
// state: DisclosureState.InvisibleUnmounted,
// attributes: { id: 'headlessui-disclosure-button-1' },
// })
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
assertDisclosureButton({
state: DisclosureState.InvisibleUnmounted,
attributes: { id: 'headlessui-disclosure-button-1' },
})
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// await click(getDisclosureButton())
await click(getDisclosureButton())
// assertDisclosureButton({
// state: DisclosureState.Visible,
// attributes: { id: 'headlessui-disclosure-button-1' },
// })
// assertDisclosurePanel({ state: DisclosureState.Visible, textContent: 'Panel is: open' })
// })
// )
assertDisclosureButton({
state: DisclosureState.Visible,
attributes: { id: 'headlessui-disclosure-button-1' },
})
assertDisclosurePanel({ state: DisclosureState.Visible, textContent: 'Panel is: open' })
})
)
// it('should be possible to render a Disclosure in an open state by default', async () => {
// render(
// <Disclosure defaultOpen>
// {({ open }) => (
// <>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>Panel is: {open ? 'open' : 'closed'}</DisclosurePanel>
// </>
// )}
// </Disclosure>
// )
it('should be possible to render a Disclosure in an open state by default', async () => {
render(svelte`
<Disclosure defaultOpen let:open>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel>Panel is: {open ? 'open' : 'closed'}</DisclosurePanel>
</Disclosure>
`)
// assertDisclosureButton({
// state: DisclosureState.Visible,
// attributes: { id: 'headlessui-disclosure-button-1' },
// })
// assertDisclosurePanel({ state: DisclosureState.Visible, textContent: 'Panel is: open' })
assertDisclosureButton({
state: DisclosureState.Visible,
attributes: { id: 'headlessui-disclosure-button-1' },
})
assertDisclosurePanel({ state: DisclosureState.Visible, textContent: 'Panel is: open' })
// await click(getDisclosureButton())
await click(getDisclosureButton())
// assertDisclosureButton({ state: DisclosureState.InvisibleUnmounted })
// })
assertDisclosureButton({ state: DisclosureState.InvisibleUnmounted })
})
// it(
// 'should expose a close function that closes the disclosure',
// suppressConsoleLogs(async () => {
// render(
// <Disclosure>
// {({ close }) => (
// <>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>
// <button onClick={() => close()}>Close me</button>
// </DisclosurePanel>
// </>
// )}
// </Disclosure>
// )
it(
'should expose a close function that closes the disclosure',
suppressConsoleLogs(async () => {
render(svelte`
<Disclosure let:close>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel>
<button on:click={() => close()}>Close me</button>
</DisclosurePanel>
</Disclosure>
`)
// // Focus the button
// getDisclosureButton()?.focus()
// Focus the button
getDisclosureButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getDisclosureButton())
// Ensure the button is focused
assertActiveElement(getDisclosureButton())
// // Open the disclosure
// await click(getDisclosureButton())
// Open the disclosure
await click(getDisclosureButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the disclosure is closed
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// Ensure the disclosure is closed
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// // Ensure the DisclosureButton got the restored focus
// assertActiveElement(getByText('Trigger'))
// })
// )
// Ensure the DisclosureButton got the restored focus
assertActiveElement(getByText('Trigger'))
})
)
// it(
// 'should expose a close function that closes the disclosure and restores to a specific element',
// suppressConsoleLogs(async () => {
// render(
// <>
// <button id="test">restoreable</button>
// <Disclosure>
// {({ close }) => (
// <>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>
// <button onClick={() => close(document.getElementById('test')!)}>
// Close me
// </button>
// </DisclosurePanel>
// </>
// )}
// </Disclosure>
// </>
// )
it(
'should expose a close function that closes the disclosure and restores to a specific element',
suppressConsoleLogs(async () => {
render(svelte`
<button id="test">restoreable</button>
<Disclosure let:close>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel>
<button on:click={() => close(document.getElementById('test'))}>
Close me
</button>
</DisclosurePanel>
</Disclosure>
`)
// // Focus the button
// getDisclosureButton()?.focus()
// Focus the button
getDisclosureButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getDisclosureButton())
// Ensure the button is focused
assertActiveElement(getDisclosureButton())
// // Open the disclosure
// await click(getDisclosureButton())
// Open the disclosure
await click(getDisclosureButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the disclosure is closed
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// Ensure the disclosure is closed
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// it(
// 'should expose a close function that closes the disclosure and restores to a ref',
// suppressConsoleLogs(async () => {
// function Example() {
// let elementRef = useRef(null)
// return (
// <>
// <button ref={elementRef}>restoreable</button>
// <Disclosure>
// {({ close }) => (
// <>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>
// <button onClick={() => close(elementRef)}>Close me</button>
// </DisclosurePanel>
// </>
// )}
// </Disclosure>
// </>
// )
// }
// render(<Example />)
// // Focus the button
// getDisclosureButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getDisclosureButton())
// // Open the disclosure
// await click(getDisclosureButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// // Ensure the disclosure is closed
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// })
// Ensure the restoreable button got the restored focus
assertActiveElement(getByText('restoreable'))
})
)
})
describe("DisclosureButton", () => {
// it(
// 'should be possible to render a DisclosureButton using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Disclosure>
// <DisclosureButton>{JSON.stringify}</DisclosureButton>
// <DisclosurePanel></DisclosurePanel>
// </Disclosure>
// )
it(
'should render a DisclosureButton with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Disclosure let:open>
<DisclosureButton>{JSON.stringify({ open })}</DisclosureButton>
<DisclosurePanel></DisclosurePanel>
</Disclosure>
`)
// assertDisclosureButton({
// state: DisclosureState.InvisibleUnmounted,
// attributes: { id: 'headlessui-disclosure-button-1' },
// textContent: JSON.stringify({ open: false }),
// })
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
assertDisclosureButton({
state: DisclosureState.InvisibleUnmounted,
attributes: { id: 'headlessui-disclosure-button-1' },
textContent: JSON.stringify({ open: false }),
})
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// await click(getDisclosureButton())
await click(getDisclosureButton())
// assertDisclosureButton({
// state: DisclosureState.Visible,
// attributes: { id: 'headlessui-disclosure-button-1' },
// textContent: JSON.stringify({ open: true }),
// })
// assertDisclosurePanel({ state: DisclosureState.Visible })
// })
// )
assertDisclosureButton({
state: DisclosureState.Visible,
attributes: { id: 'headlessui-disclosure-button-1' },
textContent: JSON.stringify({ open: true }),
})
assertDisclosurePanel({ state: DisclosureState.Visible })
})
)
// it(
// 'should be possible to render a DisclosureButton using a render prop and an `as` prop',
// suppressConsoleLogs(async () => {
// render(
// <Disclosure>
// <DisclosureButton as="div" role="button">
// {JSON.stringify}
// </DisclosureButton>
// <DisclosurePanel />
// </Disclosure>
// )
it(
'should be possible to render a DisclosureButton using a render prop and an `as` prop',
suppressConsoleLogs(async () => {
render(svelte`
<Disclosure>
<DisclosureButton as="div" role="button" let:open>
{JSON.stringify({ open })}
</DisclosureButton>
<DisclosurePanel />
</Disclosure>
`)
// assertDisclosureButton({
// state: DisclosureState.InvisibleUnmounted,
// attributes: { id: 'headlessui-disclosure-button-1' },
// textContent: JSON.stringify({ open: false }),
// })
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
assertDisclosureButton({
state: DisclosureState.InvisibleUnmounted,
attributes: { id: 'headlessui-disclosure-button-1' },
textContent: JSON.stringify({ open: false }),
})
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// await click(getDisclosureButton())
await click(getDisclosureButton())
// assertDisclosureButton({
// state: DisclosureState.Visible,
// attributes: { id: 'headlessui-disclosure-button-1' },
// textContent: JSON.stringify({ open: true }),
// })
// assertDisclosurePanel({ state: DisclosureState.Visible })
// })
// )
assertDisclosureButton({
state: DisclosureState.Visible,
attributes: { id: 'headlessui-disclosure-button-1' },
textContent: JSON.stringify({ open: true }),
})
assertDisclosurePanel({ state: DisclosureState.Visible })
})
)
describe('`type` attribute', () => {
it('should set the `type` to "button" by default', async () => {
@@ -354,34 +293,34 @@ describe("Rendering", () => {
})
describe('DisclosurePanel', () => {
// it(
// 'should be possible to render DisclosurePanel using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Disclosure>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>{JSON.stringify}</DisclosurePanel>
// </Disclosure>
// )
it(
'should render a DisclosurePanel with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Disclosure>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel let:open>{JSON.stringify({ open })}</DisclosurePanel>
</Disclosure>
`)
// assertDisclosureButton({
// state: DisclosureState.InvisibleUnmounted,
// attributes: { id: 'headlessui-disclosure-button-1' },
// })
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
assertDisclosureButton({
state: DisclosureState.InvisibleUnmounted,
attributes: { id: 'headlessui-disclosure-button-1' },
})
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// await click(getDisclosureButton())
await click(getDisclosureButton())
// assertDisclosureButton({
// state: DisclosureState.Visible,
// attributes: { id: 'headlessui-disclosure-button-1' },
// })
// assertDisclosurePanel({
// state: DisclosureState.Visible,
// textContent: JSON.stringify({ open: true }),
// })
// })
// )
assertDisclosureButton({
state: DisclosureState.Visible,
attributes: { id: 'headlessui-disclosure-button-1' },
})
assertDisclosurePanel({
state: DisclosureState.Visible,
textContent: JSON.stringify({ open: true }),
})
})
)
it('should be possible to always render the DisclosurePanel if we provide it a `static` prop', () => {
render(
@@ -427,114 +366,70 @@ describe("Rendering", () => {
assertDisclosurePanel({ state: DisclosureState.InvisibleHidden })
})
// it(
// 'should expose a close function that closes the disclosure',
// suppressConsoleLogs(async () => {
// render(
// <Disclosure>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>
// {({ close }) => <button onClick={() => close()}>Close me</button>}
// </DisclosurePanel>
// </Disclosure>
// )
it(
'should expose a close function that closes the disclosure',
suppressConsoleLogs(async () => {
render(svelte`
<Disclosure>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel let:close>
<button on:click={() => close()}>Close me</button>
</DisclosurePanel>
</Disclosure>
`)
// // Focus the button
// getDisclosureButton()?.focus()
// Focus the button
getDisclosureButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getDisclosureButton())
// Ensure the button is focused
assertActiveElement(getDisclosureButton())
// // Open the disclosure
// await click(getDisclosureButton())
// Open the disclosure
await click(getDisclosureButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the disclosure is closed
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// Ensure the disclosure is closed
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// // Ensure the DisclosureButton got the restored focus
// assertActiveElement(getByText('Trigger'))
// })
// )
// Ensure the DisclosureButton got the restored focus
assertActiveElement(getByText('Trigger'))
})
)
// it(
// 'should expose a close function that closes the disclosure and restores to a specific element',
// suppressConsoleLogs(async () => {
// render(
// <>
// <button id="test">restoreable</button>
// <Disclosure>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>
// {({ close }) => (
// <button onClick={() => close(document.getElementById('test')!)}>Close me</button>
// )}
// </DisclosurePanel>
// </Disclosure>
// </>
// )
it(
'should expose a close function that closes the disclosure and restores to a specific element',
suppressConsoleLogs(async () => {
render(svelte`
<button id="test">restoreable</button>
<Disclosure>
<DisclosureButton>Trigger</DisclosureButton>
<DisclosurePanel let:close>
<button on:click={() => close(document.getElementById('test'))}>Close me</button>
</DisclosurePanel>
</Disclosure>
`)
// // Focus the button
// getDisclosureButton()?.focus()
// Focus the button
getDisclosureButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getDisclosureButton())
// Ensure the button is focused
assertActiveElement(getDisclosureButton())
// // Open the disclosure
// await click(getDisclosureButton())
// Open the disclosure
await click(getDisclosureButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the disclosure is closed
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// Ensure the disclosure is closed
assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// it(
// 'should expose a close function that closes the disclosure and restores to a ref',
// suppressConsoleLogs(async () => {
// function Example() {
// let elementRef = useRef(null)
// return (
// <>
// <button ref={elementRef}>restoreable</button>
// <Disclosure>
// <DisclosureButton>Trigger</DisclosureButton>
// <DisclosurePanel>
// {({ close }) => <button onClick={() => close(elementRef)}>Close me</button>}
// </DisclosurePanel>
// </Disclosure>
// </>
// )
// }
// render(<Example />)
// // Focus the button
// getDisclosureButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getDisclosureButton())
// // Open the disclosure
// await click(getDisclosureButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// // Ensure the disclosure is closed
// assertDisclosurePanel({ state: DisclosureState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// Ensure the restoreable button got the restored focus
assertActiveElement(getByText('restoreable'))
})
)
})
})

View File

@@ -15,6 +15,8 @@ import {
assertListboxButton,
assertListboxButtonLinkedWithListbox,
assertListboxButtonLinkedWithListboxLabel,
assertListboxLabel,
assertListboxLabelLinkedWithListbox,
assertListboxOption,
assertNoActiveListboxOption,
assertNoSelectedListboxOption,
@@ -45,6 +47,7 @@ import ManagedListbox from "./_ManagedListbox.svelte";
import Button from "$lib/internal/elements/Button.svelte";
import Div from "$lib/internal/elements/Div.svelte";
import Span from "$lib/internal/elements/Span.svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock('../../hooks/use-id', () => {
@@ -103,41 +106,37 @@ describe('safeguards', () => {
describe('Rendering', () => {
describe('Listbox', () => {
// it(
// 'should be possible to render a Listbox using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={undefined} onChange={console.log}>
// {({ open }) => (
// <>
// <ListboxButton>Trigger</ListboxButton>
// {open && (
// <ListboxOptions>
// <ListboxOption value="a">Option A</ListboxOption>
// <ListboxOption value="b">Option B</ListboxOption>
// <ListboxOption value="c">Option C</ListboxOption>
// </ListboxOptions>
// )}
// </>
// )}
// </Listbox>
// )
it(
'should render a Listbox using slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} on:change={console.log} let:open>
<ListboxButton>Trigger</ListboxButton>
{#if open}
<ListboxOptions>
<ListboxOption value="a">Option A</ListboxOption>
<ListboxOption value="b">Option B</ListboxOption>
<ListboxOption value="c">Option C</ListboxOption>
</ListboxOptions>
{/if}
</Listbox>
`)
// assertListboxButton({
// state: ListboxState.InvisibleUnmounted,
// attributes: { id: 'headlessui-listbox-button-1' },
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxButton({
state: ListboxState.InvisibleUnmounted,
attributes: { id: 'headlessui-listbox-button-1' },
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
await click(getListboxButton())
// assertListboxButton({
// state: ListboxState.Visible,
// attributes: { id: 'headlessui-listbox-button-1' },
// })
// assertListbox({ state: ListboxState.Visible })
// })
// )
assertListboxButton({
state: ListboxState.Visible,
attributes: { id: 'headlessui-listbox-button-1' },
})
assertListbox({ state: ListboxState.Visible })
})
)
it(
'should be possible to disable a Listbox',
@@ -182,142 +181,142 @@ describe('Rendering', () => {
})
describe('ListboxLabel', () => {
// it(
// 'should be possible to render a ListboxLabel using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={ undefined } onChange = { console.log } >
// <ListboxLabel>{ JSON.stringify } < /ListboxLabel>
// < ListboxButton > Trigger < /ListboxButton>
// < ListboxOptions >
// <ListboxOption value="a" > Option A < /ListboxOption>
// < ListboxOption value = "b" > Option B < /ListboxOption>
// < ListboxOption value = "c" > Option C < /ListboxOption>
// < /ListboxOptions>
// < /Listbox>
// )
it(
'should be possible to render a ListboxLabel using a render prop',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} on:change={console.log}>
<ListboxLabel let:open let:disabled>{JSON.stringify({ open, disabled })}</ListboxLabel>
<ListboxButton>Trigger</ListboxButton>
<ListboxOptions>
<ListboxOption value="a"> Option A </ListboxOption>
<ListboxOption value="b"> Option B </ListboxOption>
<ListboxOption value="c"> Option C </ListboxOption>
</ListboxOptions>
</Listbox>
`)
// assertListboxButton({
// state: ListboxState.InvisibleUnmounted,
// attributes: { id: 'headlessui-listbox-button-2' },
// })
// assertListboxLabel({
// attributes: { id: 'headlessui-listbox-label-1' },
// textContent: JSON.stringify({ open: false, disabled: false }),
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxButton({
state: ListboxState.InvisibleUnmounted,
attributes: { id: 'headlessui-listbox-button-2' },
})
assertListboxLabel({
attributes: { id: 'headlessui-listbox-label-1' },
textContent: JSON.stringify({ open: false, disabled: false }),
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
await click(getListboxButton())
// assertListboxLabel({
// attributes: { id: 'headlessui-listbox-label-1' },
// textContent: JSON.stringify({ open: true, disabled: false }),
// })
// assertListbox({ state: ListboxState.Visible })
// assertListboxLabelLinkedWithListbox()
// assertListboxButtonLinkedWithListboxLabel()
// })
// )
assertListboxLabel({
attributes: { id: 'headlessui-listbox-label-1' },
textContent: JSON.stringify({ open: true, disabled: false }),
})
assertListbox({ state: ListboxState.Visible })
assertListboxLabelLinkedWithListbox()
assertListboxButtonLinkedWithListboxLabel()
})
)
// it(
// 'should be possible to render a ListboxLabel using a render prop and an `as` prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={ undefined } onChange = { console.log } >
// <ListboxLabel as="p" > { JSON.stringify } < /ListboxLabel>
// < ListboxButton > Trigger < /ListboxButton>
// < ListboxOptions >
// <ListboxOption value="a" > Option A < /ListboxOption>
// < ListboxOption value = "b" > Option B < /ListboxOption>
// < ListboxOption value = "c" > Option C < /ListboxOption>
// < /ListboxOptions>
// < /Listbox>
// )
it(
'should be possible to render a ListboxLabel with slot props and an `as` prop',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} on:change={console.log}>
<ListboxLabel as="p" let:open let:disabled>{JSON.stringify({ open, disabled })}</ListboxLabel>
<ListboxButton>Trigger</ListboxButton>
<ListboxOptions>
<ListboxOption value="a">Option A</ListboxOption>
<ListboxOption value="b">Option B</ListboxOption>
<ListboxOption value="c">Option C</ListboxOption>
</ListboxOptions>
</Listbox>
`)
// assertListboxLabel({
// attributes: { id: 'headlessui-listbox-label-1' },
// textContent: JSON.stringify({ open: false, disabled: false }),
// tag: 'p',
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxLabel({
attributes: { id: 'headlessui-listbox-label-1' },
textContent: JSON.stringify({ open: false, disabled: false }),
tag: 'p',
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
// assertListboxLabel({
// attributes: { id: 'headlessui-listbox-label-1' },
// textContent: JSON.stringify({ open: true, disabled: false }),
// tag: 'p',
// })
// assertListbox({ state: ListboxState.Visible })
// })
// )
await click(getListboxButton())
assertListboxLabel({
attributes: { id: 'headlessui-listbox-label-1' },
textContent: JSON.stringify({ open: true, disabled: false }),
tag: 'p',
})
assertListbox({ state: ListboxState.Visible })
})
)
});
describe("ListboxButton", () => {
// it(
// 'should be possible to render a ListboxButton using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={ undefined } onChange = { console.log } >
// <ListboxButton>{ JSON.stringify } < /ListboxButton>
// < ListboxOptions >
// <ListboxOption value="a" > Option A < /ListboxOption>
// < ListboxOption value = "b" > Option B < /ListboxOption>
// < ListboxOption value = "c" > Option C < /ListboxOption>
// < /ListboxOptions>
// < /Listbox>
// )
it(
'should render a ListboxButton with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} on:change={console.log}>
<ListboxButton let:open let:disabled>{JSON.stringify({ open, disabled})}</ListboxButton>
<ListboxOptions>
<ListboxOption value="a">Option A </ListboxOption>
<ListboxOption value="b">Option B </ListboxOption>
<ListboxOption value="c">Option C </ListboxOption>
</ListboxOptions>
</Listbox>
`)
// assertListboxButton({
// state: ListboxState.InvisibleUnmounted,
// attributes: { id: 'headlessui-listbox-button-1' },
// textContent: JSON.stringify({ open: false, disabled: false }),
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxButton({
state: ListboxState.InvisibleUnmounted,
attributes: { id: 'headlessui-listbox-button-1' },
textContent: JSON.stringify({ open: false, disabled: false }),
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
await click(getListboxButton())
// assertListboxButton({
// state: ListboxState.Visible,
// attributes: { id: 'headlessui-listbox-button-1' },
// textContent: JSON.stringify({ open: true, disabled: false }),
// })
// assertListbox({ state: ListboxState.Visible })
// })
// )
assertListboxButton({
state: ListboxState.Visible,
attributes: { id: 'headlessui-listbox-button-1' },
textContent: JSON.stringify({ open: true, disabled: false }),
})
assertListbox({ state: ListboxState.Visible })
})
)
// it(
// 'should be possible to render a ListboxButton using a render prop and an `as` prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={ undefined } onChange = { console.log } >
// <ListboxButton as="div" role = "button" >
// { JSON.stringify }
// < /ListboxButton>
// < ListboxOptions >
// <ListboxOption value="a" > Option A < /ListboxOption>
// < ListboxOption value = "b" > Option B < /ListboxOption>
// < ListboxOption value = "c" > Option C < /ListboxOption>
// < /ListboxOptions>
// < /Listbox>
// )
it(
'should be possible to render a ListboxButton using a render prop and an `as` prop',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} onChange={console.log}>
<ListboxButton as="div" role="button" let:open let:disabled>
{JSON.stringify({ open, disabled })}
</ListboxButton>
<ListboxOptions>
<ListboxOption value="a">Option A</ListboxOption>
<ListboxOption value="b">Option B</ListboxOption>
<ListboxOption value="c">Option C</ListboxOption>
</ListboxOptions>
</Listbox>
`)
// assertListboxButton({
// state: ListboxState.InvisibleUnmounted,
// attributes: { id: 'headlessui-listbox-button-1' },
// textContent: JSON.stringify({ open: false, disabled: false }),
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxButton({
state: ListboxState.InvisibleUnmounted,
attributes: { id: 'headlessui-listbox-button-1' },
textContent: JSON.stringify({ open: false, disabled: false }),
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
await click(getListboxButton())
// assertListboxButton({
// state: ListboxState.Visible,
// attributes: { id: 'headlessui-listbox-button-1' },
// textContent: JSON.stringify({ open: true, disabled: false }),
// })
// assertListbox({ state: ListboxState.Visible })
// })
// )
assertListboxButton({
state: ListboxState.Visible,
attributes: { id: 'headlessui-listbox-button-1' },
textContent: JSON.stringify({ open: true, disabled: false }),
})
assertListbox({ state: ListboxState.Visible })
})
)
it(
'should be possible to render a ListboxButton and a ListboxLabel and see them linked together',
@@ -393,41 +392,37 @@ describe('Rendering', () => {
})
describe('ListboxOptions', () => {
// it(
// 'should be possible to render ListboxOptions using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={undefined} onChange={console.log}>
// <ListboxButton>Trigger</ListboxButton>
// <ListboxOptions>
// {data => (
// <>
// <ListboxOption value="a">{JSON.stringify(data)}</ListboxOption>
// </>
// )}
// </ListboxOptions>
// </Listbox>
// )
it(
'should render ListboxOptions with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} on:change={console.log}>
<ListboxButton>Trigger</ListboxButton>
<ListboxOptions let:open>
<ListboxOption value="a">{JSON.stringify({ open })}</ListboxOption>
</ListboxOptions>
</Listbox>
`)
// assertListboxButton({
// state: ListboxState.InvisibleUnmounted,
// attributes: { id: 'headlessui-listbox-button-1' },
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxButton({
state: ListboxState.InvisibleUnmounted,
attributes: { id: 'headlessui-listbox-button-1' },
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
await click(getListboxButton())
// assertListboxButton({
// state: ListboxState.Visible,
// attributes: { id: 'headlessui-listbox-button-1' },
// })
// assertListbox({
// state: ListboxState.Visible,
// textContent: JSON.stringify({ open: true }),
// })
// assertActiveElement(getListbox())
// })
// )
assertListboxButton({
state: ListboxState.Visible,
attributes: { id: 'headlessui-listbox-button-1' },
})
assertListbox({
state: ListboxState.Visible,
textContent: JSON.stringify({ open: true }),
})
assertActiveElement(getListbox())
})
)
it('should be possible to always render the ListboxOptions if we provide it a `static` prop', () => {
render(
@@ -472,38 +467,40 @@ describe('Rendering', () => {
})
})
// describe('ListboxOption', () => {
// it(
// 'should be possible to render a ListboxOption using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Listbox value={undefined} onChange={console.log}>
// <ListboxButton>Trigger</ListboxButton>
// <ListboxOptions>
// <ListboxOption value="a">{JSON.stringify}</ListboxOption>
// </ListboxOptions>
// </Listbox>
// )
describe('ListboxOption', () => {
it(
'should render a ListboxOption with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Listbox value={undefined} on:change={console.log}>
<ListboxButton>Trigger</ListboxButton>
<ListboxOptions>
<ListboxOption value="a" let:active let:selected let:disabled>
{JSON.stringify({ active, selected, disabled })}
</ListboxOption>
</ListboxOptions>
</Listbox>
`)
// assertListboxButton({
// state: ListboxState.InvisibleUnmounted,
// attributes: { id: 'headlessui-listbox-button-1' },
// })
// assertListbox({ state: ListboxState.InvisibleUnmounted })
assertListboxButton({
state: ListboxState.InvisibleUnmounted,
attributes: { id: 'headlessui-listbox-button-1' },
})
assertListbox({ state: ListboxState.InvisibleUnmounted })
// await click(getListboxButton())
await click(getListboxButton())
// assertListboxButton({
// state: ListboxState.Visible,
// attributes: { id: 'headlessui-listbox-button-1' },
// })
// assertListbox({
// state: ListboxState.Visible,
// textContent: JSON.stringify({ active: false, selected: false, disabled: false }),
// })
// })
// )
// })
assertListboxButton({
state: ListboxState.Visible,
attributes: { id: 'headlessui-listbox-button-1' },
})
assertListbox({
state: ListboxState.Visible,
textContent: JSON.stringify({ active: false, selected: false, disabled: false }),
})
})
)
})
})
describe('Rendering composition', () => {

View File

@@ -10,6 +10,7 @@ import Button from "$lib/internal/elements/Button.svelte";
import Div from "$lib/internal/elements/Div.svelte";
import Form from "$lib/internal/elements/Form.svelte";
import Span from "$lib/internal/elements/Span.svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock('../../hooks/use-id', () => {
@@ -66,110 +67,106 @@ describe('Safe guards', () => {
})
describe('Rendering', () => {
// describe('Menu', () => {
// it(
// 'should be possible to render a Menu using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Menu>
// {({ open }) => (
// <>
// <Menu.Button>Trigger</Menu.Button>
// {open && (
// <Menu.Items>
// <Menu.Item as="a">Item A</Menu.Item>
// <Menu.Item as="a">Item B</Menu.Item>
// <Menu.Item as="a">Item C</Menu.Item>
// </Menu.Items>
// )}
// </>
// )}
// </Menu>
// )
describe('Menu', () => {
it(
'Menu should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Menu let:open>
<MenuButton>Trigger</MenuButton>
{#if open}
<MenuItems>
<MenuItem as="a">Item A</MenuItem>
<MenuItem as="a">Item B</MenuItem>
<MenuItem as="a">Item C</MenuItem>
</MenuItems>
{/if}
</Menu>
`)
// assertMenuButton({
// state: MenuState.InvisibleUnmounted,
// attributes: { id: 'headlessui-menu-button-1' },
// })
// assertMenu({ state: MenuState.InvisibleUnmounted })
assertMenuButton({
state: MenuState.InvisibleUnmounted,
attributes: { id: 'headlessui-menu-button-1' },
})
assertMenu({ state: MenuState.InvisibleUnmounted })
// await click(getMenuButton())
await click(getMenuButton())
// assertMenuButton({
// state: MenuState.Visible,
// attributes: { id: 'headlessui-menu-button-1' },
// })
// assertMenu({ state: MenuState.Visible })
// })
// )
// })
assertMenuButton({
state: MenuState.Visible,
attributes: { id: 'headlessui-menu-button-1' },
})
assertMenu({ state: MenuState.Visible })
})
)
})
describe('Menu.Button', () => {
// it(
// 'should be possible to render a Menu.Button using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Menu>
// <Menu.Button>{JSON.stringify}</Menu.Button>
// <Menu.Items>
// <Menu.Item as="a">Item A</Menu.Item>
// <Menu.Item as="a">Item B</Menu.Item>
// <Menu.Item as="a">Item C</Menu.Item>
// </Menu.Items>
// </Menu>
// )
describe('MenuButton', () => {
it(
'MenuButton should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Menu>
<MenuButton let:open>{open}</MenuButton>
<MenuItems>
<MenuItem as="a">Item A</MenuItem>
<MenuItem as="a">Item B</MenuItem>
<MenuItem as="a">Item C</MenuItem>
</MenuItems>
</Menu>
`)
// assertMenuButton({
// state: MenuState.InvisibleUnmounted,
// attributes: { id: 'headlessui-menu-button-1' },
// textContent: JSON.stringify({ open: false }),
// })
// assertMenu({ state: MenuState.InvisibleUnmounted })
assertMenuButton({
state: MenuState.InvisibleUnmounted,
attributes: { id: 'headlessui-menu-button-1' },
textContent: "false",
})
assertMenu({ state: MenuState.InvisibleUnmounted })
// await click(getMenuButton())
await click(getMenuButton())
// assertMenuButton({
// state: MenuState.Visible,
// attributes: { id: 'headlessui-menu-button-1' },
// textContent: JSON.stringify({ open: true }),
// })
// assertMenu({ state: MenuState.Visible })
// })
// )
assertMenuButton({
state: MenuState.Visible,
attributes: { id: 'headlessui-menu-button-1' },
textContent: "true",
})
assertMenu({ state: MenuState.Visible })
})
)
// it(
// 'should be possible to render a Menu.Button using a render prop and an `as` prop',
// suppressConsoleLogs(async () => {
// render(
// <Menu>
// <Menu.Button as="div" role="button">
// {JSON.stringify}
// </Menu.Button>
// <Menu.Items>
// <Menu.Item as="a">Item A</Menu.Item>
// <Menu.Item as="a">Item B</Menu.Item>
// <Menu.Item as="a">Item C</Menu.Item>
// </Menu.Items>
// </Menu>
// )
it(
'MenuButton should have slot props and support an `as` prop',
suppressConsoleLogs(async () => {
render(svelte`
<Menu>
<MenuButton as="div" role="button" let:open>
{open}
</MenuButton>
<MenuItems>
<MenuItem as="a">Item A</MenuItem>
<MenuItem as="a">Item B</MenuItem>
<MenuItem as="a">Item C</MenuItem>
</MenuItems>
</Menu>
`)
// assertMenuButton({
// state: MenuState.InvisibleUnmounted,
// attributes: { id: 'headlessui-menu-button-1' },
// textContent: JSON.stringify({ open: false }),
// })
// assertMenu({ state: MenuState.InvisibleUnmounted })
assertMenuButton({
state: MenuState.InvisibleUnmounted,
attributes: { id: 'headlessui-menu-button-1' },
textContent: "false",
})
assertMenu({ state: MenuState.InvisibleUnmounted })
// await click(getMenuButton())
await click(getMenuButton())
// assertMenuButton({
// state: MenuState.Visible,
// attributes: { id: 'headlessui-menu-button-1' },
// textContent: JSON.stringify({ open: true }),
// })
// assertMenu({ state: MenuState.Visible })
// })
// )
assertMenuButton({
state: MenuState.Visible,
attributes: { id: 'headlessui-menu-button-1' },
textContent: "true",
})
assertMenu({ state: MenuState.Visible })
})
)
describe('`type` attribute', () => {
it('should set the `type` to "button" by default', async () => {
@@ -214,43 +211,39 @@ describe('Rendering', () => {
})
})
describe('Menu.Items', () => {
// it(
// 'should be possible to render Menu.Items using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Menu>
// <Menu.Button>Trigger</Menu.Button>
// <Menu.Items>
// {data => (
// <>
// <Menu.Item as="a">{JSON.stringify(data)}</Menu.Item>
// </>
// )}
// </Menu.Items>
// </Menu>
// )
describe('MenuItems', () => {
it(
'MenuItems should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Menu>
<MenuButton>Trigger</MenuButton>
<MenuItems let:open>
<MenuItem as="a">{open}</MenuItem>
</MenuItems>
</Menu>
`)
// assertMenuButton({
// state: MenuState.InvisibleUnmounted,
// attributes: { id: 'headlessui-menu-button-1' },
// })
// assertMenu({ state: MenuState.InvisibleUnmounted })
assertMenuButton({
state: MenuState.InvisibleUnmounted,
attributes: { id: 'headlessui-menu-button-1' },
})
assertMenu({ state: MenuState.InvisibleUnmounted })
// await click(getMenuButton())
await click(getMenuButton())
// assertMenuButton({
// state: MenuState.Visible,
// attributes: { id: 'headlessui-menu-button-1' },
// })
// assertMenu({
// state: MenuState.Visible,
// textContent: JSON.stringify({ open: true }),
// })
// })
// )
assertMenuButton({
state: MenuState.Visible,
attributes: { id: 'headlessui-menu-button-1' },
})
assertMenu({
state: MenuState.Visible,
textContent: "true",
})
})
)
it('should be possible to always render the Menu.Items if we provide it a `static` prop', () => {
it('should be possible to always render the MenuItems if we provide it a `static` prop', () => {
render(
TestRenderer, {
allProps: [
@@ -269,7 +262,7 @@ describe('Rendering', () => {
expect(getMenu()).not.toBe(null)
})
it('should be possible to use a different render strategy for the Menu.Items', async () => {
it('should be possible to use a different render strategy for the MenuItems', async () => {
render(
TestRenderer, {
allProps: [
@@ -293,38 +286,38 @@ describe('Rendering', () => {
})
})
// describe('Menu.Item', () => {
// it(
// 'should be possible to render a Menu.Item using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Menu>
// <Menu.Button>Trigger</Menu.Button>
// <Menu.Items>
// <Menu.Item as="a">{JSON.stringify}</Menu.Item>
// </Menu.Items>
// </Menu>
// )
describe('MenuItem', () => {
it(
'MenuItem should have slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Menu>
<MenuButton>Trigger</MenuButton>
<MenuItems>
<MenuItem as="a" let:active let:disabled>{JSON.stringify({ active, disabled })}</MenuItem>
</MenuItems>
</Menu>
`)
// assertMenuButton({
// state: MenuState.InvisibleUnmounted,
// attributes: { id: 'headlessui-menu-button-1' },
// })
// assertMenu({ state: MenuState.InvisibleUnmounted })
assertMenuButton({
state: MenuState.InvisibleUnmounted,
attributes: { id: 'headlessui-menu-button-1' },
})
assertMenu({ state: MenuState.InvisibleUnmounted })
// await click(getMenuButton())
await click(getMenuButton())
// assertMenuButton({
// state: MenuState.Visible,
// attributes: { id: 'headlessui-menu-button-1' },
// })
// assertMenu({
// state: MenuState.Visible,
// textContent: JSON.stringify({ active: false, disabled: false }),
// })
// })
// )
// })
assertMenuButton({
state: MenuState.Visible,
attributes: { id: 'headlessui-menu-button-1' },
})
assertMenu({
state: MenuState.Visible,
textContent: JSON.stringify({ active: false, disabled: false }),
})
})
)
})
})
describe('Rendering composition', () => {
@@ -421,7 +414,7 @@ describe('Rendering composition', () => {
)
it(
'should mark all the elements between Menu.Items and Menu.Item with role none',
'should mark all the elements between MenuItems and MenuItem with role none',
suppressConsoleLogs(async () => {
render
render(
@@ -472,7 +465,7 @@ describe('Rendering composition', () => {
describe('Composition', () => {
it.skip(
'should be possible to wrap the Menu.Items with a Transition component',
'should be possible to wrap the MenuItems with a Transition component',
suppressConsoleLogs(async () => {
let orderFn = jest.fn()
render(
@@ -525,7 +518,7 @@ describe('Composition', () => {
)
it.skip(
'should be possible to wrap the Menu.Items with a Transition.Child component',
'should be possible to wrap the MenuItems with a Transition.Child component',
suppressConsoleLogs(async () => {
let orderFn = jest.fn()
render(

View File

@@ -10,6 +10,7 @@ import Span from "$lib/internal/elements/Span.svelte";
import { Transition, TransitionChild } from "$lib/components/transitions";
import TransitionDebug from "$lib/components/disclosure/_TransitionDebug.svelte";
import Portal from "$lib/components/portal/Portal.svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock('../../hooks/use-id', () => {
@@ -119,216 +120,158 @@ describe('Rendering', () => {
})
describe('Popover', () => {
// it(
// 'should be possible to render a Popover using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Popover>
// {({ open }) => (
// <>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>Panel is: {open ? 'open' : 'closed'}</Popover.Panel>
// </>
// )}
// </Popover>
// )
it(
'should render a Popover with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Popover let:open>
<PopoverButton>Trigger</PopoverButton>
<PopoverPanel>Panel is: {open ? 'open' : 'closed'}</PopoverPanel>
</Popover>
`)
// assertPopoverButton({
// state: PopoverState.InvisibleUnmounted,
// attributes: { id: 'headlessui-popover-button-1' },
// })
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
assertPopoverButton({
state: PopoverState.InvisibleUnmounted,
attributes: { id: 'headlessui-popover-button-1' },
})
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// await click(getPopoverButton())
await click(getPopoverButton())
// assertPopoverButton({
// state: PopoverState.Visible,
// attributes: { id: 'headlessui-popover-button-1' },
// })
// assertPopoverPanel({ state: PopoverState.Visible, textContent: 'Panel is: open' })
// })
// )
assertPopoverButton({
state: PopoverState.Visible,
attributes: { id: 'headlessui-popover-button-1' },
})
assertPopoverPanel({ state: PopoverState.Visible, textContent: 'Panel is: open' })
})
)
// it(
// 'should expose a close function that closes the popover',
// suppressConsoleLogs(async () => {
// render(
// <Popover>
// {({ close }) => (
// <>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>
// <button onClick={() => close()}>Close me</button>
// </Popover.Panel>
// </>
// )}
// </Popover>
// )
it(
'should expose a close function that closes the popover',
suppressConsoleLogs(async () => {
render(svelte`
<Popover let:close>
<PopoverButton>Trigger</PopoverButton>
<PopoverPanel>
<button on:click={() => close()}>Close me</button>
</PopoverPanel>
</Popover>
`)
// // Focus the button
// getPopoverButton()?.focus()
// Focus the button
getPopoverButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getPopoverButton())
// Ensure the button is focused
assertActiveElement(getPopoverButton())
// // Open the popover
// await click(getPopoverButton())
// Open the popover
await click(getPopoverButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the popover is closed
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// Ensure the popover is closed
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// // Ensure the Popover.Button got the restored focus
// assertActiveElement(getByText('Trigger'))
// })
// )
// Ensure the PopoverButton got the restored focus
assertActiveElement(getByText('Trigger'))
})
)
// it(
// 'should expose a close function that closes the popover and restores to a specific element',
// suppressConsoleLogs(async () => {
// render(
// <>
// <button id="test">restoreable</button>
// <Popover>
// {({ close }) => (
// <>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>
// <button onClick={() => close(document.getElementById('test')!)}>
// Close me
// </button>
// </Popover.Panel>
// </>
// )}
// </Popover>
// </>
// )
it(
'should expose a close function that closes the popover and restores to a specific element',
suppressConsoleLogs(async () => {
render(svelte`
<button id="test">restoreable</button>
<Popover let:close>
<PopoverButton>Trigger</PopoverButton>
<PopoverPanel>
<button on:click={() => close(document.getElementById('test'))}>
Close me
</button>
</PopoverPanel>
</Popover>
`)
// // Focus the button
// getPopoverButton()?.focus()
// Focus the button
getPopoverButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getPopoverButton())
// Ensure the button is focused
assertActiveElement(getPopoverButton())
// // Open the popover
// await click(getPopoverButton())
// Open the popover
await click(getPopoverButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the popover is closed
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// Ensure the popover is closed
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// it(
// 'should expose a close function that closes the popover and restores to a ref',
// suppressConsoleLogs(async () => {
// function Example() {
// let elementRef = useRef(null)
// return (
// <>
// <button ref={elementRef}>restoreable</button>
// <Popover>
// {({ close }) => (
// <>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>
// <button onClick={() => close(elementRef)}>Close me</button>
// </Popover.Panel>
// </>
// )}
// </Popover>
// </>
// )
// }
// render(<Example />)
// // Focus the button
// getPopoverButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getPopoverButton())
// // Open the popover
// await click(getPopoverButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// // Ensure the popover is closed
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// Ensure the restoreable button got the restored focus
assertActiveElement(getByText('restoreable'))
})
)
})
describe('Popover.Button', () => {
// it(
// 'should be possible to render a Popover.Button using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Popover>
// <Popover.Button>{JSON.stringify}</Popover.Button>
// <Popover.Panel></Popover.Panel>
// </Popover>
// )
describe('PopoverButton', () => {
it(
'should render a PopoverButton with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Popover>
<PopoverButton let:open>{JSON.stringify({open})}</PopoverButton>
<PopoverPanel></PopoverPanel>
</Popover>
`)
// assertPopoverButton({
// state: PopoverState.InvisibleUnmounted,
// attributes: { id: 'headlessui-popover-button-1' },
// textContent: JSON.stringify({ open: false }),
// })
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
assertPopoverButton({
state: PopoverState.InvisibleUnmounted,
attributes: { id: 'headlessui-popover-button-1' },
textContent: JSON.stringify({ open: false }),
})
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// await click(getPopoverButton())
await click(getPopoverButton())
// assertPopoverButton({
// state: PopoverState.Visible,
// attributes: { id: 'headlessui-popover-button-1' },
// textContent: JSON.stringify({ open: true }),
// })
// assertPopoverPanel({ state: PopoverState.Visible })
// })
// )
assertPopoverButton({
state: PopoverState.Visible,
attributes: { id: 'headlessui-popover-button-1' },
textContent: JSON.stringify({ open: true }),
})
assertPopoverPanel({ state: PopoverState.Visible })
})
)
// it(
// 'should be possible to render a Popover.Button using a render prop and an `as` prop',
// suppressConsoleLogs(async () => {
// render(
// <Popover>
// <Popover.Button as="div" role="button">
// {JSON.stringify}
// </Popover.Button>
// <Popover.Panel />
// </Popover>
// )
it(
'should render a PopoverButton with a slot prop and use an `as` prop',
suppressConsoleLogs(async () => {
render(svelte`
<Popover>
<PopoverButton as="div" role="button" let:open>
{JSON.stringify({ open })}
</PopoverButton>
<PopoverPanel />
</Popover>
`)
// assertPopoverButton({
// state: PopoverState.InvisibleUnmounted,
// attributes: { id: 'headlessui-popover-button-1' },
// textContent: JSON.stringify({ open: false }),
// })
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
assertPopoverButton({
state: PopoverState.InvisibleUnmounted,
attributes: { id: 'headlessui-popover-button-1' },
textContent: JSON.stringify({ open: false }),
})
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// await click(getPopoverButton())
await click(getPopoverButton())
// assertPopoverButton({
// state: PopoverState.Visible,
// attributes: { id: 'headlessui-popover-button-1' },
// textContent: JSON.stringify({ open: true }),
// })
// assertPopoverPanel({ state: PopoverState.Visible })
// })
// )
assertPopoverButton({
state: PopoverState.Visible,
attributes: { id: 'headlessui-popover-button-1' },
textContent: JSON.stringify({ open: true }),
})
assertPopoverPanel({ state: PopoverState.Visible })
})
)
describe('`type` attribute', () => {
it('should set the `type` to "button" by default', async () => {
@@ -370,37 +313,37 @@ describe('Rendering', () => {
})
})
describe('Popover.Panel', () => {
// it(
// 'should be possible to render Popover.Panel using a render prop',
// suppressConsoleLogs(async () => {
// render(
// <Popover>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>{JSON.stringify}</Popover.Panel>
// </Popover>
// )
describe('PopoverPanel', () => {
it(
'should render PopoverPanel with slot props',
suppressConsoleLogs(async () => {
render(svelte`
<Popover>
<PopoverButton>Trigger</PopoverButton>
<PopoverPanel let:open>{JSON.stringify({ open })}</PopoverPanel>
</Popover>
`)
// assertPopoverButton({
// state: PopoverState.InvisibleUnmounted,
// attributes: { id: 'headlessui-popover-button-1' },
// })
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
assertPopoverButton({
state: PopoverState.InvisibleUnmounted,
attributes: { id: 'headlessui-popover-button-1' },
})
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// await click(getPopoverButton())
await click(getPopoverButton())
// assertPopoverButton({
// state: PopoverState.Visible,
// attributes: { id: 'headlessui-popover-button-1' },
// })
// assertPopoverPanel({
// state: PopoverState.Visible,
// textContent: JSON.stringify({ open: true }),
// })
// })
// )
assertPopoverButton({
state: PopoverState.Visible,
attributes: { id: 'headlessui-popover-button-1' },
})
assertPopoverPanel({
state: PopoverState.Visible,
textContent: JSON.stringify({ open: true }),
})
})
)
it('should be possible to always render the Popover.Panel if we provide it a `static` prop', () => {
it('should be possible to always render the PopoverPanel if we provide it a `static` prop', () => {
render(
TestRenderer, {
allProps: [
@@ -415,7 +358,7 @@ describe('Rendering', () => {
expect(getPopoverPanel()).not.toBe(null)
})
it('should be possible to use a different render strategy for the Popover.Panel', async () => {
it('should be possible to use a different render strategy for the PopoverPanel', async () => {
render(
TestRenderer, {
allProps: [
@@ -477,7 +420,7 @@ describe('Rendering', () => {
// TODO: This test doesn't work but I'm also not totally sure it should...
// calling element.focus in the browser doesn't seem to call the window focus handler
it.skip(
'should close the Popover, when Popover.Panel has the focus prop and you focus the open button',
'should close the Popover, when PopoverPanel has the focus prop and you focus the open button',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -573,120 +516,76 @@ describe('Rendering', () => {
})
)
// it(
// 'should expose a close function that closes the popover',
// suppressConsoleLogs(async () => {
// render(
// <Popover>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>
// {({ close }) => <button onClick={() => close()}>Close me</button>}
// </Popover.Panel>
// </Popover>
// )
it(
'should expose a close function that closes the popover',
suppressConsoleLogs(async () => {
render(svelte`
<Popover>
<PopoverButton>Trigger</PopoverButton>
<PopoverPanel let:close>
<button on:click={() => close()}>Close me</button>
</PopoverPanel>
</Popover>
`)
// // Focus the button
// getPopoverButton()?.focus()
// Focus the button
getPopoverButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getPopoverButton())
// Ensure the button is focused
assertActiveElement(getPopoverButton())
// // Open the popover
// await click(getPopoverButton())
// Open the popover
await click(getPopoverButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the popover is closed
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// Ensure the popover is closed
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// // Ensure the Popover.Button got the restored focus
// assertActiveElement(getByText('Trigger'))
// })
// )
// Ensure the PopoverButton got the restored focus
assertActiveElement(getByText('Trigger'))
})
)
// it(
// 'should expose a close function that closes the popover and restores to a specific element',
// suppressConsoleLogs(async () => {
// render(
// <>
// <button id="test">restoreable</button>
// <Popover>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>
// {({ close }) => (
// <button onClick={() => close(document.getElementById('test')!)}>Close me</button>
// )}
// </Popover.Panel>
// </Popover>
// </>
// )
it(
'should expose a close function that closes the popover and restores to a specific element',
suppressConsoleLogs(async () => {
render(svelte`
<button id="test">restoreable</button>
<Popover>
<PopoverButton>Trigger</PopoverButton>
<PopoverPanel let:close>
<button on:click={() => close(document.getElementById('test'))}>Close me</button>
</PopoverPanel>
</Popover>
`)
// // Focus the button
// getPopoverButton()?.focus()
// Focus the button
getPopoverButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getPopoverButton())
// Ensure the button is focused
assertActiveElement(getPopoverButton())
// // Open the popover
// await click(getPopoverButton())
// Open the popover
await click(getPopoverButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// Ensure we can click the close button
await click(getByText('Close me'))
// // Ensure the popover is closed
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// Ensure the popover is closed
assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// it(
// 'should expose a close function that closes the popover and restores to a ref',
// suppressConsoleLogs(async () => {
// function Example() {
// let elementRef = useRef(null)
// return (
// <>
// <button ref={elementRef}>restoreable</button>
// <Popover>
// <Popover.Button>Trigger</Popover.Button>
// <Popover.Panel>
// {({ close }) => <button onClick={() => close(elementRef)}>Close me</button>}
// </Popover.Panel>
// </Popover>
// </>
// )
// }
// render(<Example />)
// // Focus the button
// getPopoverButton()?.focus()
// // Ensure the button is focused
// assertActiveElement(getPopoverButton())
// // Open the popover
// await click(getPopoverButton())
// // Ensure we can click the close button
// await click(getByText('Close me'))
// // Ensure the popover is closed
// assertPopoverPanel({ state: PopoverState.InvisibleUnmounted })
// // Ensure the restoreable button got the restored focus
// assertActiveElement(getByText('restoreable'))
// })
// )
// Ensure the restoreable button got the restored focus
assertActiveElement(getByText('restoreable'))
})
)
})
})
describe('Composition', () => {
it(
'should be possible to wrap the Popover.Panel with a Transition component',
'should be possible to wrap the PopoverPanel with a Transition component',
suppressConsoleLogs(async () => {
let orderFn = jest.fn()
render(
@@ -889,7 +788,7 @@ describe('Keyboard interactions', () => {
)
it(
'should close the Popover by pressing `Enter` on a Popover.Button inside a Popover.Panel',
'should close the Popover by pressing `Enter` on a PopoverButton inside a PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -926,7 +825,7 @@ describe('Keyboard interactions', () => {
describe('`Escape` key', () => {
it(
'should close the Popover menu, when pressing escape on the Popover.Button',
'should close the Popover menu, when pressing escape on the PopoverButton',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -962,7 +861,7 @@ describe('Keyboard interactions', () => {
)
it(
'should close the Popover menu, when pressing escape on the Popover.Panel',
'should close the Popover menu, when pressing escape on the PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1006,7 +905,7 @@ describe('Keyboard interactions', () => {
)
it(
'should be possible to close a sibling Popover when pressing escape on a sibling Popover.Button',
'should be possible to close a sibling Popover when pressing escape on a sibling PopoverButton',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1059,7 +958,7 @@ describe('Keyboard interactions', () => {
describe('`Tab` key', () => {
it(
'should be possible to Tab through the panel contents onto the next Popover.Button',
'should be possible to Tab through the panel contents onto the next PopoverButton',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1261,7 +1160,7 @@ describe('Keyboard interactions', () => {
)
it(
'should close the Popover when the Popover.Panel has a focus prop',
'should close the Popover when the PopoverPanel has a focus prop',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1297,7 +1196,7 @@ describe('Keyboard interactions', () => {
)
it(
'should close the Popover when the Popover.Panel has a focus prop (Popover.Panel uses a Portal)',
'should close the Popover when the PopoverPanel has a focus prop (PopoverPanel uses a Portal)',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1343,7 +1242,7 @@ describe('Keyboard interactions', () => {
)
it(
'should close the Popover when the Popover.Panel has a focus prop (Popover.Panel uses a Portal), and focus the next focusable item in line',
'should close the Popover when the PopoverPanel has a focus prop (PopoverPanel uses a Portal), and focus the next focusable item in line',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1473,7 +1372,7 @@ describe('Keyboard interactions', () => {
)
it(
'should focus the previous Popover.Button when Shift+Tab on the second Popover.Button',
'should focus the previous PopoverButton when Shift+Tab on the second PopoverButton',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1509,19 +1408,19 @@ describe('Keyboard interactions', () => {
// Ensure the popover is now closed
assertPopoverButton({ state: PopoverState.InvisibleUnmounted }, getByText('Trigger 2'))
// Ensure the second Popover.Button is focused
// Ensure the second PopoverButton is focused
assertActiveElement(getByText('Trigger 2'))
// Tab backwards
await press(shift(Keys.Tab))
// Ensure the first Popover.Button is open
// Ensure the first PopoverButton is open
assertActiveElement(getByText('Trigger 1'))
})
)
it(
'should focus the Popover.Button when pressing Shift+Tab when we focus inside the Popover.Panel',
'should focus the PopoverButton when pressing Shift+Tab when we focus inside the PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1548,7 +1447,7 @@ describe('Keyboard interactions', () => {
// Tab out of the Panel
await press(shift(Keys.Tab))
// Ensure the Popover.Button is focused again
// Ensure the PopoverButton is focused again
assertActiveElement(getPopoverButton())
// Ensure the Popover is closed
@@ -1558,7 +1457,7 @@ describe('Keyboard interactions', () => {
)
it(
'should focus the Popover.Button when pressing Shift+Tab when we focus inside the Popover.Panel (inside a Portal)',
'should focus the PopoverButton when pressing Shift+Tab when we focus inside the PopoverPanel (inside a Portal)',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1587,7 +1486,7 @@ describe('Keyboard interactions', () => {
// Tab out of the Panel
await press(shift(Keys.Tab))
// Ensure the Popover.Button is focused again
// Ensure the PopoverButton is focused again
assertActiveElement(getPopoverButton())
// Ensure the Popover is closed
@@ -1597,7 +1496,7 @@ describe('Keyboard interactions', () => {
)
it(
'should be possible to focus the last item in the Popover.Panel when pressing Shift+Tab on the next Popover.Button',
'should be possible to focus the last item in the PopoverPanel when pressing Shift+Tab on the next PopoverButton',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1637,7 +1536,7 @@ describe('Keyboard interactions', () => {
assertPopoverButton({ state: PopoverState.Visible })
assertPopoverPanel({ state: PopoverState.Visible })
// Press shift+tab, to move focus to the last item in the Popover.Panel
// Press shift+tab, to move focus to the last item in the PopoverPanel
await press(shift(Keys.Tab), getByText('Trigger 2'))
// Verify we are focusing the last link of the first Popover
@@ -1646,7 +1545,7 @@ describe('Keyboard interactions', () => {
)
it(
"should be possible to focus the last item in the Popover.Panel when pressing Shift+Tab on the next Popover.Button (using Portal's)",
"should be possible to focus the last item in the PopoverPanel when pressing Shift+Tab on the next PopoverButton (using Portal's)",
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -1690,7 +1589,7 @@ describe('Keyboard interactions', () => {
assertPopoverButton({ state: PopoverState.Visible })
assertPopoverPanel({ state: PopoverState.Visible })
// Press shift+tab, to move focus to the last item in the Popover.Panel
// Press shift+tab, to move focus to the last item in the PopoverPanel
await press(shift(Keys.Tab), getByText('Trigger 2'))
// Verify we are focusing the last link of the first Popover
@@ -1852,7 +1751,7 @@ describe('Keyboard interactions', () => {
)
it(
'should close the Popover by pressing `Space` on a Popover.Button inside a Popover.Panel',
'should close the Popover by pressing `Space` on a PopoverButton inside a PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -2170,7 +2069,7 @@ describe('Mouse interactions', () => {
)
it(
'should be possible to close the Popover by clicking on a Popover.Button inside a Popover.Panel',
'should be possible to close the Popover by clicking on a PopoverButton inside a PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -2205,7 +2104,7 @@ describe('Mouse interactions', () => {
)
it(
'should not close the Popover when clicking on a focusable element inside a static Popover.Panel',
'should not close the Popover when clicking on a focusable element inside a static PopoverPanel',
suppressConsoleLogs(async () => {
let clickFn = jest.fn()
@@ -2236,7 +2135,7 @@ describe('Mouse interactions', () => {
)
it(
'should not close the Popover when clicking on a non-focusable element inside a static Popover.Panel',
'should not close the Popover when clicking on a non-focusable element inside a static PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {
@@ -2262,7 +2161,7 @@ describe('Mouse interactions', () => {
)
it(
'should close the Popover when clicking outside of a static Popover.Panel',
'should close the Popover when clicking outside of a static PopoverPanel',
suppressConsoleLogs(async () => {
render(
TestRenderer, {

View File

@@ -13,6 +13,7 @@ import TestRenderer from "$lib/test-utils/TestRenderer.svelte";
import { click, Keys, press, shift } from "$lib/test-utils/interactions";
import Button from "$lib/internal/elements/Button.svelte";
import ManagedRadioGroup from "./_ManagedRadioGroup.svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock('../../hooks/use-id', () => {
@@ -123,169 +124,159 @@ describe('Rendering', () => {
assertNotFocusable(getByText('Dine in'))
})
// it('should guarantee the radio option order after a few unmounts', async () => {
// function Example() {
// let [showFirst, setShowFirst] = useState(false)
// let [active, setActive] = useState()
// TODO: fix this test!
it.skip('should guarantee the radio option order after a few unmounts', async () => {
render(svelte`
<script>
let showFirst = false;
let active;
</script>
<button on:click={() => showFirst = !showFirst}>Toggle</button>
<RadioGroup value={active} on:change={(e) => active = e.detail}>
<RadioGroupLabel>Pizza Delivery</RadioGroupLabel>
{#if showFirst}
<RadioGroupOption value="pickup">Pickup</RadioGroupOption>
{/if}
<RadioGroupOption value="home-delivery">Home delivery</RadioGroupOption>
<RadioGroupOption value="dine-in">Dine in</RadioGroupOption>
</RadioGroup>
`)
// return (
// <>
// <button onClick={() => setShowFirst(v => !v)}>Toggle</button>
// <RadioGroup value={active} onChange={setActive}>
// <RadioGroup.Label>Pizza Delivery</RadioGroup.Label>
// {showFirst && <RadioGroup.Option value="pickup">Pickup</RadioGroup.Option>}
// <RadioGroup.Option value="home-delivery">Home delivery</RadioGroup.Option>
// <RadioGroup.Option value="dine-in">Dine in</RadioGroup.Option>
// </RadioGroup>
// </>
// )
// }
await click(getByText('Toggle')) // Render the pickup again
// render(<Example />)
await press(Keys.Tab) // Focus first element
assertActiveElement(getByText('Pickup'))
// await click(getByText('Toggle')) // Render the pickup again
await press(Keys.ArrowUp) // Loop around
assertActiveElement(getByText('Dine in'))
// await press(Keys.Tab) // Focus first element
// assertActiveElement(getByText('Pickup'))
await press(Keys.ArrowUp) // Up again
assertActiveElement(getByText('Home delivery'))
})
// await press(Keys.ArrowUp) // Loop around
// assertActiveElement(getByText('Dine in'))
it('should be possible to disable a RadioGroup', async () => {
let changeFn = jest.fn()
// await press(Keys.ArrowUp) // Up again
// assertActiveElement(getByText('Home delivery'))
// })
render(svelte`
<script>
let disabled = true;
</script>
<button on:click={() => disabled = !disabled}>Toggle</button>
<RadioGroup value={undefined} on:change={changeFn} {disabled}>
<RadioGroupLabel>Pizza Delivery</RadioGroupLabel>
<RadioGroupOption value="pickup">Pickup</RadioGroupOption>
<RadioGroupOption value="home-delivery">Home delivery</RadioGroupOption>
<RadioGroupOption value="dine-in">Dine in</RadioGroupOption>
<RadioGroupOption value="slot-prop" data-value="slot-prop" let:checked let:disabled let:active>
{JSON.stringify({ checked, disabled, active })}
</RadioGroupOption>
</RadioGroup>
`)
// it('should be possible to disable a RadioGroup', async () => {
// let changeFn = jest.fn()
// function Example() {
// let [disabled, setDisabled] = useState(true)
// return (
// <>
// <button onClick={() => setDisabled(v => !v)}>Toggle</button>
// <RadioGroup value={undefined} onChange={changeFn} disabled={disabled}>
// <RadioGroup.Label>Pizza Delivery</RadioGroup.Label>
// <RadioGroup.Option value="pickup">Pickup</RadioGroup.Option>
// <RadioGroup.Option value="home-delivery">Home delivery</RadioGroup.Option>
// <RadioGroup.Option value="dine-in">Dine in</RadioGroup.Option>
// <RadioGroup.Option value="render-prop" data-value="render-prop">
// {JSON.stringify}
// </RadioGroup.Option>
// </RadioGroup>
// </>
// )
// }
// Try to click one a few options
await click(getByText('Pickup'))
await click(getByText('Dine in'))
// render(<Example />)
// Verify that the RadioGroupOption gets the disabled state
expect(document.querySelector('[data-value="slot-prop"]')).toHaveTextContent(
JSON.stringify({
checked: false,
disabled: true,
active: false,
})
)
// // Try to click one a few options
// await click(getByText('Pickup'))
// await click(getByText('Dine in'))
// Make sure that the onChange handler never got called
expect(changeFn).toHaveBeenCalledTimes(0)
// // Verify that the RadioGroup.Option gets the disabled state
// expect(document.querySelector('[data-value="render-prop"]')).toHaveTextContent(
// JSON.stringify({
// checked: false,
// disabled: true,
// active: false,
// })
// )
// Make sure that all the options get an `aria-disabled`
let options = getRadioGroupOptions()
expect(options).toHaveLength(4)
for (let option of options) expect(option).toHaveAttribute('aria-disabled', 'true')
// // Make sure that the onChange handler never got called
// expect(changeFn).toHaveBeenCalledTimes(0)
// Toggle the disabled state
await click(getByText('Toggle'))
// // Make sure that all the options get an `aria-disabled`
// let options = getRadioGroupOptions()
// expect(options).toHaveLength(4)
// for (let option of options) expect(option).toHaveAttribute('aria-disabled', 'true')
// Verify that the RadioGroupOption gets the disabled state
expect(document.querySelector('[data-value="slot-prop"]')).toHaveTextContent(
JSON.stringify({
checked: false,
disabled: false,
active: false,
})
)
// // Toggle the disabled state
// await click(getByText('Toggle'))
// Try to click one a few options
await click(getByText('Pickup'))
// // Verify that the RadioGroup.Option gets the disabled state
// expect(document.querySelector('[data-value="render-prop"]')).toHaveTextContent(
// JSON.stringify({
// checked: false,
// disabled: false,
// active: false,
// })
// )
// Make sure that the onChange handler got called
expect(changeFn).toHaveBeenCalledTimes(1)
})
// // Try to click one a few options
// await click(getByText('Pickup'))
it('should be possible to disable a RadioGroupOption', async () => {
let changeFn = jest.fn()
// // Make sure that the onChange handler got called
// expect(changeFn).toHaveBeenCalledTimes(1)
// })
render(svelte`
<script>
let disabled = true;
</script>
<button on:click={() => disabled = !disabled}>Toggle</button>
<RadioGroup value={undefined} on:change={changeFn}>
<RadioGroupLabel>Pizza Delivery</RadioGroupLabel>
<RadioGroupOption value="pickup">Pickup</RadioGroupOption>
<RadioGroupOption value="home-delivery">Home delivery</RadioGroupOption>
<RadioGroupOption value="dine-in">Dine in</RadioGroupOption>
<RadioGroupOption value="slot-prop" {disabled} data-value="slot-prop" let:checked let:disabled let:active>
{JSON.stringify({ checked, disabled, active })}
</RadioGroupOption>
</RadioGroup>
`)
// it('should be possible to disable a RadioGroup.Option', async () => {
// let changeFn = jest.fn()
// Try to click the disabled option
await click(document.querySelector('[data-value="slot-prop"]'))
// function Example() {
// let [disabled, setDisabled] = useState(true)
// return (
// <>
// <button onClick={() => setDisabled(v => !v)}>Toggle</button>
// <RadioGroup value={undefined} onChange={changeFn}>
// <RadioGroup.Label>Pizza Delivery</RadioGroup.Label>
// <RadioGroup.Option value="pickup">Pickup</RadioGroup.Option>
// <RadioGroup.Option value="home-delivery">Home delivery</RadioGroup.Option>
// <RadioGroup.Option value="dine-in">Dine in</RadioGroup.Option>
// <RadioGroup.Option value="render-prop" disabled={disabled} data-value="render-prop">
// {JSON.stringify}
// </RadioGroup.Option>
// </RadioGroup>
// </>
// )
// }
// Verify that the RadioGroupOption gets the disabled state
expect(document.querySelector('[data-value="slot-prop"]')).toHaveTextContent(
JSON.stringify({
checked: false,
disabled: true,
active: false,
})
)
// render(<Example />)
// Make sure that the onChange handler never got called
expect(changeFn).toHaveBeenCalledTimes(0)
// // Try to click the disabled option
// await click(document.querySelector('[data-value="render-prop"]'))
// Make sure that the option with value "slot-prop" gets an `aria-disabled`
let options = getRadioGroupOptions()
expect(options).toHaveLength(4)
for (let option of options) {
if (option.dataset.value) {
expect(option).toHaveAttribute('aria-disabled', 'true')
} else {
expect(option).not.toHaveAttribute('aria-disabled')
}
}
// // Verify that the RadioGroup.Option gets the disabled state
// expect(document.querySelector('[data-value="render-prop"]')).toHaveTextContent(
// JSON.stringify({
// checked: false,
// disabled: true,
// active: false,
// })
// )
// Toggle the disabled state
await click(getByText('Toggle'))
// // Make sure that the onChange handler never got called
// expect(changeFn).toHaveBeenCalledTimes(0)
// Verify that the RadioGroupOption gets the disabled state
expect(document.querySelector('[data-value="slot-prop"]')).toHaveTextContent(
JSON.stringify({
checked: false,
disabled: false,
active: false,
})
)
// // Make sure that the option with value "render-prop" gets an `aria-disabled`
// let options = getRadioGroupOptions()
// expect(options).toHaveLength(4)
// for (let option of options) {
// if (option.dataset.value) {
// expect(option).toHaveAttribute('aria-disabled', 'true')
// } else {
// expect(option).not.toHaveAttribute('aria-disabled')
// }
// }
// Try to click one a few options
await click(document.querySelector('[data-value="slot-prop"]'))
// // Toggle the disabled state
// await click(getByText('Toggle'))
// // Verify that the RadioGroup.Option gets the disabled state
// expect(document.querySelector('[data-value="render-prop"]')).toHaveTextContent(
// JSON.stringify({
// checked: false,
// disabled: false,
// active: false,
// })
// )
// // Try to click one a few options
// await click(document.querySelector('[data-value="render-prop"]'))
// // Make sure that the onChange handler got called
// expect(changeFn).toHaveBeenCalledTimes(1)
// })
// })
// Make sure that the onChange handler got called
expect(changeFn).toHaveBeenCalledTimes(1)
})
})

View File

@@ -13,6 +13,7 @@ import Div from "$lib/internal/elements/Div.svelte";
import Span from "$lib/internal/elements/Span.svelte";
import ManagedSwitch from "./_ManagedSwitch.svelte";
import { click, Keys, press } from "$lib/test-utils/interactions";
import svelte from "svelte-inline-compile";
jest.mock("../../hooks/use-id");
describe("Safe guards", () => {
@@ -24,27 +25,25 @@ describe("Safe guards", () => {
});
describe("Rendering", () => {
// TODO: handle these render prop (slot prop) tests
it('(on) Switch should have a slot prop', () => {
render(svelte`
<Switch checked={true} on:change={console.log} let:checked>
<span>{checked ? 'On' : 'Off'}</span>
</Switch>
`)
// it('should be possible to render an (on) Switch using a render prop', () => {
// render(TestRenderer, {
// <Switch checked={true} onChange={console.log}>
// {({ checked }) => <span>{checked ? 'On' : 'Off'}</span>}
// </Switch>
// )
assertSwitch({ state: SwitchState.On, textContent: 'On' })
})
// assertSwitch({ state: SwitchState.On, textContent: 'On' })
// })
it('(off) Switch should have a slot prop', () => {
render(svelte`
<Switch checked={false} on:change={console.log} let:checked>
<span>{checked ? 'On' : 'Off'}</span>
</Switch>
`)
// it('should be possible to render an (off) Switch using a render prop', () => {
// render(
// <Switch checked={false} onChange={console.log}>
// {({ checked }) => <span>{checked ? 'On' : 'Off'}</span>}
// </Switch>
// )
// assertSwitch({ state: SwitchState.Off, textContent: 'Off' })
// })
assertSwitch({ state: SwitchState.Off, textContent: 'Off' })
})
it("should be possible to render an (on) Switch using an `as` prop", () => {
render(TestRenderer, {

View File

@@ -5,6 +5,7 @@ import { Tab, TabGroup, TabList, TabPanel, TabPanels } from ".";
import { assertActiveElement, assertTabs, getByText, getTabs } from "$lib/test-utils/accessibility-assertions";
import { click, Keys, press, shift } from "$lib/test-utils/interactions";
import Button from "$lib/internal/elements/Button.svelte";
import svelte from "svelte-inline-compile";
let mockId = 0;
jest.mock('../../hooks/use-id', () => {
@@ -59,7 +60,7 @@ describe('safeguards', () => {
})
describe('Rendering', () => {
it('should be possible to render the Tab.Panels first, then the Tab.List', async () => {
it('should be possible to render the TabPanels first, then the TabList', async () => {
render(
TestRenderer, {
allProps: [
@@ -81,229 +82,192 @@ describe('Rendering', () => {
assertTabs({ active: 0 })
})
// describe('`renderProps`', () => {
// it('should expose the `selectedIndex` on the `Tab.Group` component', async () => {
// render(
// <Tab.Group>
// {data => (
// <>
// <pre id="exposed">{JSON.stringify(data)}</pre>
describe('`slot props`', () => {
it('should expose the `selectedIndex` on the `TabGroup` component', async () => {
render(svelte`
<TabGroup let:selectedIndex>
<pre id="exposed">{JSON.stringify({ selectedIndex })}</pre>
// <Tab.List>
// <Tab>Tab 1</Tab>
// <Tab>Tab 2</Tab>
// <Tab>Tab 3</Tab>
// </Tab.List>
<TabList>
<Tab>Tab 1</Tab>
<Tab>Tab 2</Tab>
<Tab>Tab 3</Tab>
</TabList>
// <Tab.Panels>
// <Tab.Panel>Content 1</Tab.Panel>
// <Tab.Panel>Content 2</Tab.Panel>
// <Tab.Panel>Content 3</Tab.Panel>
// </Tab.Panels>
// </>
// )}
// </Tab.Group>
// )
<TabPanels>
<TabPanel>Content 1</TabPanel>
<TabPanel>Content 2</TabPanel>
<TabPanel>Content 3</TabPanel>
</TabPanels>
</TabGroup>
`)
// expect(document.getElementById('exposed')).toHaveTextContent(
// JSON.stringify({ selectedIndex: 0 })
// )
expect(document.getElementById('exposed')).toHaveTextContent(
JSON.stringify({ selectedIndex: 0 })
)
// await click(getByText('Tab 2'))
await click(getByText('Tab 2'))
// expect(document.getElementById('exposed')).toHaveTextContent(
// JSON.stringify({ selectedIndex: 1 })
// )
// })
expect(document.getElementById('exposed')).toHaveTextContent(
JSON.stringify({ selectedIndex: 1 })
)
})
// it('should expose the `selectedIndex` on the `Tab.List` component', async () => {
// render(
// <Tab.Group>
// <Tab.List>
// {data => (
// <>
// <pre id="exposed">{JSON.stringify(data)}</pre>
// <Tab>Tab 1</Tab>
// <Tab>Tab 2</Tab>
// <Tab>Tab 3</Tab>
// </>
// )}
// </Tab.List>
it('should expose the `selectedIndex` on the `TabList` component', async () => {
render(svelte`
<TabGroup>
<TabList let:selectedIndex>
<pre id="exposed">{ JSON.stringify({ selectedIndex }) }</pre>
<Tab>Tab 1</Tab>
<Tab>Tab 2</Tab>
<Tab>Tab 3</Tab>
</TabList>
<TabPanels>
<TabPanel>Content 1</TabPanel>
<TabPanel>Content 2</TabPanel>
<TabPanel>Content 3</TabPanel>
</TabPanels>
</TabGroup>
`)
// <Tab.Panels>
// <Tab.Panel>Content 1</Tab.Panel>
// <Tab.Panel>Content 2</Tab.Panel>
// <Tab.Panel>Content 3</Tab.Panel>
// </Tab.Panels>
// </Tab.Group>
// )
expect(document.getElementById('exposed')).toHaveTextContent(
JSON.stringify({ selectedIndex: 0 })
)
// expect(document.getElementById('exposed')).toHaveTextContent(
// JSON.stringify({ selectedIndex: 0 })
// )
await click(getByText('Tab 2'))
// await click(getByText('Tab 2'))
expect(document.getElementById('exposed')).toHaveTextContent(
JSON.stringify({ selectedIndex: 1 })
)
})
// expect(document.getElementById('exposed')).toHaveTextContent(
// JSON.stringify({ selectedIndex: 1 })
// )
// })
it('should expose the `selectedIndex` on the `TabPanels` component', async () => {
render(svelte`
<TabGroup>
<TabList>
<Tab>Tab 1</Tab>
<Tab>Tab 2</Tab>
<Tab>Tab 3</Tab>
</TabList>
// it('should expose the `selectedIndex` on the `Tab.Panels` component', async () => {
// render(
// <Tab.Group>
// <Tab.List>
// <Tab>Tab 1</Tab>
// <Tab>Tab 2</Tab>
// <Tab>Tab 3</Tab>
// </Tab.List>
<TabPanels let:selectedIndex>
<pre id="exposed">{ JSON.stringify({ selectedIndex }) }</pre>
<TabPanel>Content 1</TabPanel>
<TabPanel>Content 2</TabPanel>
<TabPanel>Content 3</TabPanel>
</TabPanels>
</TabGroup>
`)
// <Tab.Panels>
// {data => (
// <>
// <pre id="exposed">{JSON.stringify(data)}</pre>
// <Tab.Panel>Content 1</Tab.Panel>
// <Tab.Panel>Content 2</Tab.Panel>
// <Tab.Panel>Content 3</Tab.Panel>
// </>
// )}
// </Tab.Panels>
// </Tab.Group>
// )
expect(document.getElementById('exposed')).toHaveTextContent(
JSON.stringify({ selectedIndex: 0 })
)
// expect(document.getElementById('exposed')).toHaveTextContent(
// JSON.stringify({ selectedIndex: 0 })
// )
await click(getByText('Tab 2'))
// await click(getByText('Tab 2'))
expect(document.getElementById('exposed')).toHaveTextContent(
JSON.stringify({ selectedIndex: 1 })
)
})
// expect(document.getElementById('exposed')).toHaveTextContent(
// JSON.stringify({ selectedIndex: 1 })
// )
// })
it('should expose the `selected` state on the `Tab` components', async () => {
render(svelte`
<TabGroup>
<TabList>
<Tab let:selected>
<pre data-tab={0}>{JSON.stringify({selected})}</pre>
<span>Tab 1</span>
</Tab>
<Tab let:selected>
<pre data-tab={1}>{JSON.stringify({selected})}</pre>
<span>Tab 2</span>
</Tab>
<Tab let:selected>
<pre data-tab={2}>{JSON.stringify({selected})}</pre>
<span>Tab 3</span>
</Tab>
</TabList>
// it('should expose the `selected` state on the `Tab` components', async () => {
// render(
// <Tab.Group>
// <Tab.List>
// <Tab>
// {data => (
// <>
// <pre data-tab={0}>{JSON.stringify(data)}</pre>
// <span>Tab 1</span>
// </>
// )}
// </Tab>
// <Tab>
// {data => (
// <>
// <pre data-tab={1}>{JSON.stringify(data)}</pre>
// <span>Tab 2</span>
// </>
// )}
// </Tab>
// <Tab>
// {data => (
// <>
// <pre data-tab={2}>{JSON.stringify(data)}</pre>
// <span>Tab 3</span>
// </>
// )}
// </Tab>
// </Tab.List>
<TabPanels>
<TabPanel>Content 1</TabPanel>
<TabPanel>Content 2</TabPanel>
<TabPanel>Content 3</TabPanel>
</TabPanels>
</TabGroup>
`)
// <Tab.Panels>
// <Tab.Panel>Content 1</Tab.Panel>
// <Tab.Panel>Content 2</Tab.Panel>
// <Tab.Panel>Content 3</Tab.Panel>
// </Tab.Panels>
// </Tab.Group>
// )
expect(document.querySelector('[data-tab="0"]')).toHaveTextContent(
JSON.stringify({ selected: true })
)
expect(document.querySelector('[data-tab="1"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
expect(document.querySelector('[data-tab="2"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
// expect(document.querySelector('[data-tab="0"]')).toHaveTextContent(
// JSON.stringify({ selected: true })
// )
// expect(document.querySelector('[data-tab="1"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
// expect(document.querySelector('[data-tab="2"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
await click(getTabs()[1])
// await click(getTabs()[1])
expect(document.querySelector('[data-tab="0"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
expect(document.querySelector('[data-tab="1"]')).toHaveTextContent(
JSON.stringify({ selected: true })
)
expect(document.querySelector('[data-tab="2"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
})
// expect(document.querySelector('[data-tab="0"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
// expect(document.querySelector('[data-tab="1"]')).toHaveTextContent(
// JSON.stringify({ selected: true })
// )
// expect(document.querySelector('[data-tab="2"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
// })
it('should expose the `selected` state on the `TabPanel` components', async () => {
render(svelte`
<TabGroup>
<TabList>
<Tab>Tab 1</Tab>
<Tab>Tab 2</Tab>
<Tab>Tab 3</Tab>
</TabList>
// it('should expose the `selected` state on the `Tab.Panel` components', async () => {
// render(
// <Tab.Group>
// <Tab.List>
// <Tab>Tab 1</Tab>
// <Tab>Tab 2</Tab>
// <Tab>Tab 3</Tab>
// </Tab.List>
<TabPanels>
<TabPanel unmount={false} let:selected>
<pre data-panel={0}>{JSON.stringify({ selected })}</pre>
<span> Content 1 </span>
</TabPanel>
<TabPanel unmount={false} let:selected>
<pre data-panel={1}>{JSON.stringify({ selected })}</pre>
<span> Content 2 </span>
</TabPanel>
<TabPanel unmount={false} let:selected>
<pre data-panel={2}>{JSON.stringify({ selected })}</pre>
<span> Content 3 </span>
</TabPanel>
</TabPanels>
</TabGroup>
`)
// <Tab.Panels>
// <Tab.Panel unmount={false}>
// {data => (
// <>
// <pre data-panel={0}>{JSON.stringify(data)}</pre>
// <span>Content 1</span>
// </>
// )}
// </Tab.Panel>
// <Tab.Panel unmount={false}>
// {data => (
// <>
// <pre data-panel={1}>{JSON.stringify(data)}</pre>
// <span>Content 2</span>
// </>
// )}
// </Tab.Panel>
// <Tab.Panel unmount={false}>
// {data => (
// <>
// <pre data-panel={2}>{JSON.stringify(data)}</pre>
// <span>Content 3</span>
// </>
// )}
// </Tab.Panel>
// </Tab.Panels>
// </Tab.Group>
// )
expect(document.querySelector('[data-panel="0"]')).toHaveTextContent(
JSON.stringify({ selected: true })
)
expect(document.querySelector('[data-panel="1"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
expect(document.querySelector('[data-panel="2"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
// expect(document.querySelector('[data-panel="0"]')).toHaveTextContent(
// JSON.stringify({ selected: true })
// )
// expect(document.querySelector('[data-panel="1"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
// expect(document.querySelector('[data-panel="2"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
await click(getByText('Tab 2'))
// await click(getByText('Tab 2'))
// expect(document.querySelector('[data-panel="0"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
// expect(document.querySelector('[data-panel="1"]')).toHaveTextContent(
// JSON.stringify({ selected: true })
// )
// expect(document.querySelector('[data-panel="2"]')).toHaveTextContent(
// JSON.stringify({ selected: false })
// )
// })
// })
expect(document.querySelector('[data-panel="0"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
expect(document.querySelector('[data-panel="1"]')).toHaveTextContent(
JSON.stringify({ selected: true })
)
expect(document.querySelector('[data-panel="2"]')).toHaveTextContent(
JSON.stringify({ selected: false })
)
})
})
describe('`defaultIndex`', () => {
it('should jump to the nearest tab when the defaultIndex is out of bounds (-2)', async () => {