rusackas commented on code in PR #43979:
URL: https://github.com/apache/superset/pull/43979#discussion_r3963012716
##########
superset/utils/screenshot_utils.py:
##########
@@ -437,6 +437,67 @@ def _unready_chart_holders_js_body(*, viewport_only: bool)
-> str:
}}
"""
+# Content that is fully present in the DOM but visually clipped by a fixed
+# height + internal scrollbar -- e.g. a table taller than the space its
+# dashboard tile gives it. These mirror the selectors the client-side
+# "download as image" export unrolls before rasterizing
+# (superset-frontend/src/utils/downloadAsImage.tsx) so both capture paths
+# treat scrollable widgets the same way (#38090).
+SCROLLABLE_CONTENT_SELECTORS = [
+ ".ant-table-body",
+ ".table-container",
+ ".ant-table-container",
+ ".table-wrapper",
+ ".virtual-table",
+]
+
+# ag-Grid virtualizes rows for performance, so a plain height/overflow reset
+# would still leave off-screen rows unrendered. `domLayout: "print"` is
+# ag-Grid's own "render every row into the DOM" mode -- the same mode the
+# client-side image export switches to via the GridApi that
+# ThemedAgGridReact (superset-ui-core) stashes on the grid's host element
+# specifically so screenshot/export code can reach it.
+#
+# `page.screenshot(full_page=True)` already expands the outer dashboard
+# scroll to include every below-the-fold chart (#31158); it has no effect on
+# a chart's own internal scroll container, which is what this JS unrolls
+# in-place before the page is captured.
+EXPAND_SCROLLABLE_CONTENT_JS = f"""
+async () => {{
+ const agGrids = Array.from(
+ document.querySelectorAll('{AG_GRID_HOST_SELECTOR}')
+ );
+ await Promise.all(agGrids.map(async (grid) => {{
+ const api = grid._agGridApi;
+ if (!api) {{ return; }}
+ api.setGridOption('domLayout', 'print');
+ if (api.resetRowHeights) {{ api.resetRowHeights(); }}
+ let lastHeight = grid.scrollHeight;
+ let stableCount = 0;
+ const deadline = Date.now() + 5000;
+ while (Date.now() < deadline && stableCount < 5) {{
+ await new Promise((resolve) => setTimeout(resolve, 100));
Review Comment:
Fixed, threaded `report_execution_context`'s remaining deadline into this
poll instead of the fixed 5s ceiling.
##########
superset/utils/screenshot_utils.py:
##########
@@ -437,6 +437,67 @@ def _unready_chart_holders_js_body(*, viewport_only: bool)
-> str:
}}
"""
+# Content that is fully present in the DOM but visually clipped by a fixed
+# height + internal scrollbar -- e.g. a table taller than the space its
+# dashboard tile gives it. These mirror the selectors the client-side
+# "download as image" export unrolls before rasterizing
+# (superset-frontend/src/utils/downloadAsImage.tsx) so both capture paths
+# treat scrollable widgets the same way (#38090).
+SCROLLABLE_CONTENT_SELECTORS = [
+ ".ant-table-body",
+ ".table-container",
+ ".ant-table-container",
+ ".table-wrapper",
+ ".virtual-table",
+]
+
+# ag-Grid virtualizes rows for performance, so a plain height/overflow reset
+# would still leave off-screen rows unrendered. `domLayout: "print"` is
+# ag-Grid's own "render every row into the DOM" mode -- the same mode the
+# client-side image export switches to via the GridApi that
+# ThemedAgGridReact (superset-ui-core) stashes on the grid's host element
+# specifically so screenshot/export code can reach it.
+#
+# `page.screenshot(full_page=True)` already expands the outer dashboard
+# scroll to include every below-the-fold chart (#31158); it has no effect on
+# a chart's own internal scroll container, which is what this JS unrolls
+# in-place before the page is captured.
+EXPAND_SCROLLABLE_CONTENT_JS = f"""
+async () => {{
+ const agGrids = Array.from(
+ document.querySelectorAll('{AG_GRID_HOST_SELECTOR}')
+ );
+ await Promise.all(agGrids.map(async (grid) => {{
+ const api = grid._agGridApi;
+ if (!api) {{ return; }}
+ api.setGridOption('domLayout', 'print');
+ if (api.resetRowHeights) {{ api.resetRowHeights(); }}
+ let lastHeight = grid.scrollHeight;
+ let stableCount = 0;
+ const deadline = Date.now() + 5000;
+ while (Date.now() < deadline && stableCount < 5) {{
+ await new Promise((resolve) => setTimeout(resolve, 100));
+ const height = grid.scrollHeight;
+ if (height === lastHeight) {{
+ stableCount += 1;
+ }} else {{
+ stableCount = 0;
+ lastHeight = height;
+ }}
+ }}
+ }}));
+
+ const scrollableSelectors = {SCROLLABLE_CONTENT_SELECTORS!r};
+ scrollableSelectors.forEach((selector) => {{
+ document.querySelectorAll(selector).forEach((el) => {{
+ el.style.overflow = 'visible';
+ el.style.height = 'auto';
+ el.style.maxHeight = 'none';
+ }});
Review Comment:
Fixed. Growing the descendant alone didn't do it, `.slice_container` and the
ag-Grid wrapper's own fixed height needed resetting too so `.chart-container`'s
bounding box actually grows.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]