Skip to content
This repository was archived by the owner on Mar 4, 2020. It is now read-only.
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 15 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,21 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm

## [Unreleased]

<!--------------------------------[ v0.34.3 ]------------------------------- -->
## [v0.34.3](https://github.com/stardust-ui/react/tree/v0.34.3) (2019-07-23)
[Compare changes](https://github.com/stardust-ui/react/compare/v0.34.2...v0.34.3)

### Fixes
- Fix nesting issues with `Dialog` component inside `Popup` @layershifter ([#1706](https://github.com/stardust-ui/react/pull/1706))

<!--------------------------------[ v0.34.2 ]------------------------------- -->
## [v0.34.2](https://github.com/stardust-ui/react/tree/v0.34.2) (2019-07-19)
[Compare changes](https://github.com/stardust-ui/react/compare/v0.34.1...v0.34.2)

### Fixes
- Fix a gap in `Checkbox` in RTL mode @layershifter ([#1683](https://github.com/stardust-ui/react/pull/1683))
- Fix broken background in `Popup` with `pointing` and `FocusTrap` @layershifter ([#1689](https://github.com/stardust-ui/react/pull/1689))

<!--------------------------------[ v0.34.1 ]------------------------------- -->
## [v0.34.1](https://github.com/stardust-ui/react/tree/v0.34.1) (2019-07-11)
[Compare changes](https://github.com/stardust-ui/react/compare/v0.34.0...v0.34.1)
Expand Down
6 changes: 6 additions & 0 deletions docs/src/components/Sidebar/Sidebar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -437,6 +437,12 @@ class Sidebar extends React.Component<any, any> {
to: '/prototype-popups',
styles: menuItemStyles,
},
{
key: 'nested-popups-and-dialogs',
content: 'Nested Popups & Dialogs',
as: NavLink,
to: '/prototype-nested-popups-and-dialogs',
},
{
key: 'iconviewer',
content: 'Processed Icons',
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import * as React from 'react'
import { Checkbox, Divider, Flex } from '@stardust-ui/react'

const CheckboxExampleRtl = () => (
<Flex column hAlign="start">
<Checkbox label="لروسية عدد, كلّ لغزو" />
<Checkbox label="Lorem ipsum dolor sit amet" />
<Divider />
<Checkbox label="لروسية عدد, كلّ لغزو" labelPosition="start" />
<Checkbox label="Lorem ipsum dolor sit amet" labelPosition="start" />
</Flex>
)

export default CheckboxExampleRtl
12 changes: 12 additions & 0 deletions docs/src/examples/components/Checkbox/Rtl/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import * as React from 'react'

import ComponentExample from 'docs/src/components/ComponentDoc/ComponentExample'
import NonPublicSection from 'docs/src/components/ComponentDoc/NonPublicSection'

const Rtl = () => (
<NonPublicSection title="Rtl">
<ComponentExample examplePath="components/Checkbox/Rtl/CheckboxExample.rtl" />
</NonPublicSection>
)

export default Rtl
2 changes: 2 additions & 0 deletions docs/src/examples/components/Checkbox/index.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import * as React from 'react'

import Rtl from './Rtl'
import Slots from './Slots'
import States from './States'
import Types from './Types'
Expand All @@ -9,6 +10,7 @@ const CheckboxExamples = () => (
<Types />
<States />
<Slots />
<Rtl />
</>
)

Expand Down
129 changes: 129 additions & 0 deletions docs/src/prototypes/NestedPopupsAndDialogs/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,129 @@
import { Button, Dialog, Popup } from '@stardust-ui/react'
import * as React from 'react'

import { ComponentPrototype, PrototypeSection } from 'docs/src/prototypes/Prototypes'

const PopupAndDialog: React.FC = () => (
<Popup
content={{
content: (
<>
<p>
This <code>Popup</code> will be kept open after <code>Dialog</code> will be opened.
</p>
<Dialog
cancelButton="Close"
header="A dialog"
trigger={<Button content="Open a dialog" />}
/>
</>
),
}}
trigger={<Button content="Open a popup" />}
/>
)

const ControlledPopupAndDialog: React.FC = () => {
const [dialogOpen, setDialogOpen] = React.useState(false)
const [popupOpen, setPopupOpen] = React.useState(false)

return (
<>
<Popup
content={{
content: (
<>
<p>
This <code>Popup</code> will be close after <code>Dialog</code> will be opened.
</p>
<Button
content="Open a dialog & close popup"
onClick={() => {
setPopupOpen(false)
setDialogOpen(true)
}}
/>
</>
),
}}
onOpenChange={(e, data) => setPopupOpen(data.open)}
open={popupOpen}
trigger={<Button content="Open a popup" />}
/>
<Dialog
cancelButton="Close"
header="A dialog"
onCancel={() => setDialogOpen(false)}
open={dialogOpen}
/>
</>
)
}

const NestedDialogs: React.FC = () => (
<Dialog
cancelButton="Close"
header="An outer dialog"
content={{
content: (
<>
<p>
This <code>Dialog</code> contains another <code>Dialog</code> inside.
</p>
<blockquote>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor
incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud
exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure
dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.
Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt
mollit anim id est laborum.
</blockquote>

<Dialog
cancelButton="Close"
header="An inner dialog"
content={
<>
<p>
This <code>Dialog</code> is nested ヽ(^o^)ノ, if you will on an overlay only this{' '}
<code>Dialog</code> will be closed.
</p>

<Popup
content="You can have also Popups inside dialogs!"
trigger={<Button content="Open a popup" />}
/>
</>
}
trigger={<Button content="Open a dialog" />}
/>
</>
),
}}
trigger={<Button content="Open a dialog" />}
/>
)

const NestedPopupsAndDialogs: React.FC = () => {
return (
<PrototypeSection title="Nested Popups & Dialogs">
<ComponentPrototype
title="A popup with dialog"
description="Popup will be kept open after Dialog"
>
<PopupAndDialog />
</ComponentPrototype>
<ComponentPrototype
title="A closable popup with dialog"
description="Popup will be closed once Dialog will be opened"
>
<ControlledPopupAndDialog />
</ComponentPrototype>
<ComponentPrototype title="Nested dialogs" description="An example with nested dialogs">
<NestedDialogs />
</ComponentPrototype>
</PrototypeSection>
)
}

export default NestedPopupsAndDialogs
7 changes: 7 additions & 0 deletions docs/src/routes.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ import PopupsPrototype from './prototypes/popups'
import IconViewerPrototype from './prototypes/IconViewer'
import MenuButtonPrototype from './prototypes/MenuButton'
import AlertsPrototype from './prototypes/alerts'
import NestedPopupsAndDialogsPrototype from './prototypes/NestedPopupsAndDialogs'

const Router = () => (
<BrowserRouter basename={__BASENAME__}>
Expand Down Expand Up @@ -126,6 +127,12 @@ const Router = () => (
path="/prototype-alerts"
component={AlertsPrototype}
/>,
<DocsLayout
exact
key="/prototype-nested-popups-and-dialogs"
path="/prototype-nested-popups-and-dialogs"
component={NestedPopupsAndDialogsPrototype}
/>,
]}
<DocsLayout exact path="/faq" component={FAQ} />
<DocsLayout exact path="/accessibility" component={Accessibility} />
Expand Down
7 changes: 7 additions & 0 deletions e2e/e2eApi.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,13 @@ export class E2EApi {

public clickOn = async (selector: string) => await (await this.getElement(selector)).click()

public clickOnPosition = async (selector: string, x: number, y: number) => {
const elementHandle = await this.getElement(selector)
const boundingBox = await elementHandle.boundingBox()

await this.page.mouse.click(Math.round(boundingBox.x) + x, Math.round(boundingBox.y) + y)
}

public textOf = async (selector: string) => {
const element = await this.getElement(selector)
return await (await element.getProperty('textContent')).jsonValue()
Expand Down
35 changes: 35 additions & 0 deletions e2e/tests/dialogInDialog-example.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import * as React from 'react'
import { Button, Dialog } from '@stardust-ui/react'

export const selectors = {
outerClose: 'outer-close',
outerHeader: 'outer-header',
outerTrigger: 'outer-trigger',
outerOverlay: 'outer-overlay',

innerClose: 'inner-close',
innerHeader: 'inner-header',
innerTrigger: 'inner-trigger',
innerOverlay: 'inner-overlay',
}

const DialogInPopupExample = () => (
<Dialog
cancelButton={{ content: 'Close', id: selectors.outerClose }}
content={{
content: (
<Dialog
cancelButton={{ content: 'Close', id: selectors.innerClose }}
header={{ content: 'An inner', id: selectors.innerHeader }}
overlay={{ id: selectors.innerOverlay }}
trigger={<Button id={selectors.innerTrigger} content="Open a dialog" />}
/>
),
}}
header={{ content: 'An outer', id: selectors.outerHeader }}
overlay={{ id: selectors.outerOverlay }}
trigger={<Button id={selectors.outerTrigger} content="Open a dialog" />}
/>
)

export default DialogInPopupExample
62 changes: 62 additions & 0 deletions e2e/tests/dialogInDialog-test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
import { selectors } from './dialogInDialog-example'

const outerClose = `#${selectors.outerClose}`
const outerHeader = `#${selectors.outerHeader}`
const outerOverlay = `#${selectors.outerOverlay}`
const outerTrigger = `#${selectors.outerTrigger}`
const innerClose = `#${selectors.innerClose}`
const innerHeader = `#${selectors.innerHeader}`
const innerTrigger = `#${selectors.innerTrigger}`
const innerOverlay = `#${selectors.innerOverlay}`

// https://github.com/stardust-ui/react/issues/1674
describe('Dialog in Dialog', () => {
beforeEach(async () => {
await e2e.gotoTestCase(__filename, outerTrigger)
})

it('An outer "Dialog" should be open after inner "Dialog" will be opened', async () => {
await e2e.clickOn(outerTrigger)
expect(await e2e.exists(outerHeader)).toBe(true)

await e2e.clickOn(innerTrigger)
expect(await e2e.exists(outerHeader)).toBe(true)
expect(await e2e.exists(innerHeader)).toBe(true)
})

it('A click inside inner "Dialog" should not close dialogs', async () => {
await e2e.clickOn(outerTrigger)
await e2e.clickOn(innerTrigger)
await e2e.clickOn(innerHeader)

expect(await e2e.exists(outerHeader)).toBe(true)
expect(await e2e.exists(innerHeader)).toBe(true)
})

it('A click on overlay should close only the last opened "Dialog"', async () => {
await e2e.clickOn(outerTrigger)
await e2e.clickOn(innerTrigger)

await e2e.clickOnPosition(innerOverlay, 0, 0)

expect(await e2e.exists(outerHeader)).toBe(true)
expect(await e2e.exists(innerHeader)).toBe(false)

await e2e.clickOnPosition(outerOverlay, 0, 0)
expect(await e2e.exists(outerHeader)).toBe(false)
expect(await e2e.exists(innerHeader)).toBe(false)
})

it('A click on cancel button should close only matching "Dialog"', async () => {
await e2e.clickOn(outerTrigger)
await e2e.clickOn(innerTrigger)

await e2e.clickOn(innerClose)
expect(await e2e.exists(outerHeader)).toBe(true)
expect(await e2e.exists(innerHeader)).toBe(false)

await e2e.clickOn(outerClose)
expect(await e2e.exists(outerHeader)).toBe(false)
expect(await e2e.exists(innerHeader)).toBe(false)
})
})
28 changes: 28 additions & 0 deletions e2e/tests/dialogInPopup-example.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import * as React from 'react'
import { Button, Dialog, Popup } from '@stardust-ui/react'

export const selectors = {
dialogCancel: 'dialog-cancel',
dialogHeader: Dialog.slotClassNames.header,
dialogOverlay: Dialog.slotClassNames.overlay,
dialogTrigger: 'dialog-trigger',
popupContent: Popup.Content.className,
popupTrigger: 'popup-trigger',
}

const DialogInPopupExample = () => (
<Popup
content={{
content: (
<Dialog
cancelButton={{ content: 'Close', id: selectors.dialogCancel }}
header="A dialog"
trigger={<Button id={selectors.dialogTrigger} content="Open a dialog" />}
/>
),
}}
trigger={<Button id={selectors.popupTrigger} content="Open a popup" />}
/>
)

export default DialogInPopupExample
Loading