Skip to content
This repository was archived by the owner on Mar 4, 2020. It is now read-only.
Merged
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
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm
- Fix comparison for `scrollParent` in `unstable_Popper` @layershifter ([#1959](https://github.com/stardust-ui/react/pull/1959))
- Updating `Button` styles for Teams dark & high contrast themes to match design @notandrew ([#1933](https://github.com/stardust-ui/react/pull/1933))
- Update Office brand icons in Teams theme with latest version @notandrew ([#1954](https://github.com/stardust-ui/react/pull/1954))
- Fix setting `data-whatinput` attribute in child windows @layershifter ([#1972](https://github.com/stardust-ui/react/pull/1972))
- Avoid usages of global `document` and `window` in components @layershifter ([#1970](https://github.com/stardust-ui/react/pull/1970))

### Features
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import { Attachment, Button, Provider, themes } from '@stardust-ui/react'
import * as React from 'react'
import * as ReactDOM from 'react-dom'

type PortalFrameProps = {
children: (externalDocument: Document) => React.ReactElement
}

const PortalFrame: React.FunctionComponent<PortalFrameProps> = ({ children }) => {
const frameRef = React.useRef<HTMLIFrameElement>(null)
const [mounted, setMounted] = React.useState<boolean>(false)

React.useEffect(() => {
setMounted(true)
}, [])

return (
<>
<iframe
ref={frameRef}
style={{ height: 300, width: 600, border: 0, padding: 20 }}
title="An example of nested Provider in iframe"
/>
{mounted &&
ReactDOM.createPortal(
children(frameRef.current.contentDocument),
frameRef.current.contentDocument.body,
)}
</>
)
}

const ProviderExampleTargetFrame = () => (
<PortalFrame>
{externalDocument => (
<Provider theme={themes.teams} target={externalDocument}>
<Attachment actionable header="Document.docx" />
<Button content="Hello world!" />
</Provider>
)}
</PortalFrame>
)

export default ProviderExampleTargetFrame
8 changes: 8 additions & 0 deletions docs/src/examples/components/Provider/Usage/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,14 @@ const Usage = () => (
description="A Provider allows to define target document to apply styles."
examplePath="components/Provider/Usage/ProviderExampleTarget"
/>
<ComponentExample
description={
<>
<code>iframe</code> can be also used as <code>target</code>.
</>
}
examplePath="components/Provider/Usage/ProviderExampleTargetFrame"
/>
</ExampleSection>
)

Expand Down
44 changes: 5 additions & 39 deletions packages/react/src/lib/whatInput.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,6 @@ import isBrowser from './isBrowser'
* variables
*/

// cache document.documentElement

const docElem = isBrowser() ? document.documentElement : null

// currently focused dom element
let currentElement = null

// last used input type
let currentInput = 'initial'

Expand Down Expand Up @@ -83,7 +76,7 @@ const setUp = () => {
inputMap[detectWheel()] = 'mouse'

addListeners(window)
doUpdate()
doUpdate(window.document)
}

/*
Expand Down Expand Up @@ -117,10 +110,6 @@ const addListeners = (eventTarget: Window) => {
// keyboard events
eventTarget.addEventListener('keydown', eventBuffer, true)
eventTarget.addEventListener('keyup', eventBuffer, true)

// focus events
eventTarget.addEventListener('focusin', setElement)
eventTarget.addEventListener('focusout', clearElement)
}

// checks conditions before updating new input
Expand All @@ -145,37 +134,14 @@ const setInput = event => {
window.sessionStorage.setItem('what-input', currentInput)
} catch (e) {}

doUpdate()
doUpdate(event.view.document)
}
}
}

// updates the doc and `inputTypes` array with new input
const doUpdate = () => {
docElem.setAttribute(`data-whatinput`, currentInput)
}

const setElement = event => {
if (!event.target.nodeName) {
// If nodeName is undefined, clear the element
// This can happen if click inside an <svg> element.
clearElement()
return
}

currentElement = event.target.nodeName.toLowerCase()
docElem.setAttribute('data-whatelement', currentElement)

if (event.target.classList && event.target.classList.length) {
docElem.setAttribute('data-whatclasses', event.target.classList.toString().replace(' ', ','))
}
}
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We don't use data-whatclasses & data-whatelement, so it's safe to remove them


const clearElement = () => {
currentElement = null

docElem.removeAttribute('data-whatelement')
docElem.removeAttribute('data-whatclasses')
const doUpdate = (target: Document) => {
target.documentElement.setAttribute(`data-whatinput`, currentInput)
}

// buffers events that frequently also fire mouse events
Expand Down Expand Up @@ -253,7 +219,7 @@ export const setUpWhatInput = (target: Document) => {
target[whatInputInitialized] = true

addListeners(targetWindow)
doUpdate()
doUpdate(target)
}
}

Expand Down