From 6d98b8b29aa8410be9dd99f423d94e3540019fce Mon Sep 17 00:00:00 2001 From: Peter McKenna Date: Thu, 13 Sep 2018 07:35:18 +0100 Subject: [PATCH] fix: run getComputedStyle in the same context as the target element (#678) I work on an embedded JavaScript app. We inject an iframe into the page that we're embedded on and the JavaScript is inserted and run in the context of that iframe so we can run in isolation from the parent page. This works well, [but there's an issue in Firefox, specifically with `getComputedStyle()`](https://bugzilla.mozilla.org/show_bug.cgi?id=548397), where, if you try to run this method in the context of an iframe, it always returns `null`. I'm looking to introduce Popper into my embedded app, but because of the bug above, Popper can't position my elements because `getComputedStyle` returns `null`. Unfortunately, this issue has been open for almost a decade and is unlikely to be fixed any time soon. Because the elements themselves live on the parent page, we can work around this by getting the window of the document that the element is embedded in, and run `getComputedStyle()` in that context. This PR solves our specific use case, and should work exactly as before for any other supported browser. Let me know what you think. --- packages/popper/src/utils/getOuterSizes.js | 3 ++- packages/popper/src/utils/getStyleComputedProperty.js | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/packages/popper/src/utils/getOuterSizes.js b/packages/popper/src/utils/getOuterSizes.js index e5e60213b6..6a266b5072 100644 --- a/packages/popper/src/utils/getOuterSizes.js +++ b/packages/popper/src/utils/getOuterSizes.js @@ -6,7 +6,8 @@ * @returns {Object} object containing width and height properties */ export default function getOuterSizes(element) { - const styles = getComputedStyle(element); + const window = element.ownerDocument.defaultView; + const styles = window.getComputedStyle(element); const x = parseFloat(styles.marginTop) + parseFloat(styles.marginBottom); const y = parseFloat(styles.marginLeft) + parseFloat(styles.marginRight); const result = { diff --git a/packages/popper/src/utils/getStyleComputedProperty.js b/packages/popper/src/utils/getStyleComputedProperty.js index e2b245793c..014f32bb8e 100644 --- a/packages/popper/src/utils/getStyleComputedProperty.js +++ b/packages/popper/src/utils/getStyleComputedProperty.js @@ -10,6 +10,7 @@ export default function getStyleComputedProperty(element, property) { return []; } // NOTE: 1 DOM access here - const css = getComputedStyle(element, null); + const window = element.ownerDocument.defaultView; + const css = window.getComputedStyle(element, null); return property ? css[property] : css; }