Skip to content
This repository has been archived by the owner on Mar 12, 2024. It is now read-only.

Hack-fix labels on safari when scrolling #222

Merged
merged 1 commit into from
Nov 4, 2021
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
7 changes: 5 additions & 2 deletions src/component.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ import { ErrorDisplay, HeaderBar } from "./header";
import { HiPlotPluginData, DataProviderClass } from "./plugin";
import { StaticDataProvider } from "./dataproviders/static";
import { uncompress } from "./lib/compress";

import { setupBrowserCompat } from "./lib/browsercompat";

//@ts-ignore
import LogoSVG from "../hiplot/static/logo.svg";
Expand Down Expand Up @@ -152,6 +152,7 @@ export function createDefaultPlugins(): PluginsMap {
export class HiPlot extends React.Component<HiPlotProps, HiPlotState> {
// React refs
contextMenuRef = React.createRef<ContextMenu>();
rootRef = React.createRef<HTMLDivElement>();

plugins_window_state: {[plugin: string]: any} = {};

Expand Down Expand Up @@ -322,6 +323,8 @@ export class HiPlot extends React.Component<HiPlotProps, HiPlotState> {
this.callFilteredUidsHooks.cancel();
}
componentDidMount() {
setupBrowserCompat(this.rootRef.current);

// Setup contextmenu when we right-click a parameter
this.contextMenuRef.current.addCallback(this.columnContextMenu.bind(this), this);

Expand Down Expand Up @@ -532,7 +535,7 @@ export class HiPlot extends React.Component<HiPlotProps, HiPlotState> {
};
}.bind(this);
return (
<div className={`hip_thm--${this.state.dark ? "dark" : "light"}`}>
<div ref={this.rootRef} className={`hip_thm--${this.state.dark ? "dark" : "light"}`}>
<div className={style.hiplot}>
<SelectedCountProgressBar {...controlProps} />
<HeaderBar
Expand Down
29 changes: 29 additions & 0 deletions src/lib/browsercompat.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@

export const IS_SAFARI = /^((?!chrome|android).)*safari/i.test(navigator.userAgent);

export function redrawObject(fo: SVGForeignObjectElement) {
const parent = fo.parentNode;
parent.removeChild(fo);
parent.appendChild(fo);

}
export function redrawAllForeignObjectsIfSafari() {
if (!IS_SAFARI) {
return;
}
const fo = document.getElementsByTagName("foreignObject");
Array.from(fo).forEach(redrawObject);
}

export function setupBrowserCompat(root: HTMLDivElement) {
/**
* Safari has a lot of trouble with foreignObjects inside canvas. Especially when we apply rotations, etc...
* As it considers the parent of the objects inside the FO to be the canvas origin, and not the FO.
* See https://stackoverflow.com/questions/51313873/svg-foreignobject-not-working-properly-on-safari
* Applying the fix in the link above fixes their position upon scroll - we don't want that, so we
* manually force-redraw them upon scroll.
*/
if (IS_SAFARI) {
root.addEventListener("wheel", redrawAllForeignObjectsIfSafari);
}
}
4 changes: 2 additions & 2 deletions src/lib/svghelpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import { ParamDef } from "../infertypes";
import style from "../hiplot.scss";
import { ContextMenu } from "../contextmenu";


function leftPos(anchor: string, w: number, minmax?: [number, number]): number {
var left = {
end: -w,
Expand Down Expand Up @@ -51,8 +52,7 @@ export function foCreateAxisLabel(pd: ParamDef, cm?: React.RefObject<ContextMenu
var fo = document.createElementNS('http://www.w3.org/2000/svg',"foreignObject");
const span = d3.select(fo).append("xhtml:div")
.classed(style.tooltipContainer, true)
.classed(style.label, true)
.style("position", "fixed"); // BUGFIX for transforms in Safari (https://stackoverflow.com/questions/51313873/svg-foreignobject-not-working-properly-on-safari)
.classed(style.label, true);
span.append("xhtml:span")
.attr("class", pd.label_css)
.classed("label-name", true)
Expand Down
15 changes: 13 additions & 2 deletions src/parallel/parallel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import { HiPlotPluginData } from "../plugin";
import { ResizableH } from "../lib/resizable";
import { Filter, FilterType, apply_filters } from "../filters";
import { foDynamicSizeFitContent, foCreateAxisLabel } from "../lib/svghelpers";
import { IS_SAFARI, redrawAllForeignObjectsIfSafari } from "../lib/browsercompat";

interface StringMapping<V> { [key: string]: V; };

Expand Down Expand Up @@ -152,10 +153,11 @@ export class ParallelPlot extends React.Component<ParallelPlotData, ParallelPlot
this.xscale.domain(this.state.dimensions);
this.dimensions_dom.filter(function(this: ParallelPlot, p) { return this.state.dimensions.indexOf(p) == -1; }.bind(this)).remove();
this.dimensions_dom = this.dimensions_dom.filter(function(this: ParallelPlot, p) { return this.state.dimensions.indexOf(p) !== -1; }.bind(this));
if (!this.state.dragging) {
if (!this.state.dragging && !IS_SAFARI) {
g = g.transition();
}
g.attr("transform", function(this: ParallelPlot, p) { return "translate(" + this.position(p) + ")"; }.bind(this));
redrawAllForeignObjectsIfSafari();
this.update_ticks();
this.updateAxisTitlesAnglesAndFontSize();
}
Expand Down Expand Up @@ -349,14 +351,19 @@ export class ParallelPlot extends React.Component<ParallelPlotData, ParallelPlot
me.setState({dimensions: new_dimensions});
}
me.dimensions_dom.attr("transform", function(d) { return "translate(" + me.position(d) + ")"; });
redrawAllForeignObjectsIfSafari();
})
.on("end", function(d: string) {
if (!me.state.dragging.dragging) {
// no movement, invert axis
var extent = invert_axis(d);
} else {
// reorder axes
d3.select(this).transition().attr("transform", "translate(" + me.xscale(d) + ")");
var drag: any = d3.select(this);
if (!IS_SAFARI) {
drag = drag.transition();
}
drag.attr("transform", "translate(" + me.xscale(d) + ")");
var extents = brush_extends();
extent = extents[d];
}
Expand Down Expand Up @@ -612,6 +619,7 @@ export class ParallelPlot extends React.Component<ParallelPlotData, ParallelPlot
.each(function(d: string) {
d3.select(this).call(me.axis.scale(me.yscale[d]));
});
me.updateAxisTitlesAnglesAndFontSize();

// render data
this.setState(function(prevState) { return { brush_count: prevState.brush_count + 1}; });
Expand Down Expand Up @@ -682,6 +690,9 @@ export class ParallelPlot extends React.Component<ParallelPlotData, ParallelPlot
));
this.style.fontSize = newFontSize + "px";
this.style.transform = "rotate(" + (360 - ROTATION_ANGLE_RADS * 180 / Math.PI) + "deg)";
if (IS_SAFARI) {
this.parentElement.style.position = "fixed";
}
const fo = this.parentElement.parentElement as any as SVGForeignObjectElement;
fo.setAttribute("y", -newFontSize + "");
});
Expand Down