Last active
April 12, 2020 09:27
-
-
Save sp0033212000/faf2d03c91433123d1123afd852f59a9 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { useState, useEffect, useRef, useCallback } from "react"; | |
import ReactDOM from "react-dom"; | |
const UseBlankWindow = ({ children, closeWindowPortal }) => { | |
const [containerEl, setContainerEl] = useState(null); | |
const externalWindow = useRef(null); | |
useEffect(() => { | |
//open a new window without url (you could specific title here if you want) | |
externalWindow.current = window.open( | |
"", | |
"", | |
//setting initial window size | |
`width=${width},height=${height},top=300px, left=500px` | |
); | |
const el = document.createElement("div"); | |
//additional option, you could setting this element in here. | |
el.id = "root"; | |
externalWindow.current.document.body.appendChild(el); | |
//additional option, you could setting new window document in here. | |
externalWindow.current.document.title = "New Window"; | |
//copy css here | |
copyStyle(document, externalWindow.current.document); | |
setContainerEl(el); | |
//the behavior after close window. eg. setShowWindow(false) | |
externalWindow.current.addEventListener("beforeunload", () => { | |
closeWindowPortal(); | |
}); | |
return () => { | |
//trigger close behavior when this component unmount | |
externalWindow.current.close(); | |
}; | |
// eslint-disable-next-line react-hooks/exhaustive-deps | |
}, []); | |
const renderEl = useCallback(() => { | |
if (containerEl === null) return null; | |
const child = React.cloneElement(children, { | |
portalDOM: externalWindow.current, | |
}); | |
return ReactDOM.createPortal(child, containerEl); | |
}, [containerEl, children]); | |
return renderEl(); | |
}; | |
function copyStyle(sourceDom, targetDom) { | |
Array.from(sourceDom.styleSheets).forEach((styleSheet) => { | |
let newLinkEl = null; | |
//Note! The style loaded from a URL should load first! | |
if (styleSheet.href) { | |
newLinkEl = sourceDom.createElement("link"); | |
newLinkEl.rel = "stylesheet"; | |
newLinkEl.href = styleSheet.href; | |
} else if (styleSheet.cssRules) { | |
newLinkEl = sourceDom.createElement("style"); | |
Array.from(styleSheet.cssRules).forEach((cssRules) => { | |
newLinkEl.appendChild(sourceDom.createTextNode(cssRules.cssText)); | |
}); | |
} | |
targetDom.head.appendChild(newLinkEl); | |
}); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment