in src/popover/popover.tsx [426:491]
render() {
const mountedAndOpen = this.state.isMounted && (this.props.isOpen || this.state.isAnimating);
const rendered = [this.renderAnchor()];
const renderedContent = mountedAndOpen || this.props.renderAll ? this.renderContent() : null;
const defaultPopperOptions = {
modifiers: {
preventOverflow: { enabled: !this.props.ignoreBoundary, padding: 0 },
},
};
// Only render popover on the browser (portals aren't supported server-side)
if (renderedContent) {
if (mountedAndOpen) {
rendered.push(
<Layer
key="new-layer"
mountNode={this.props.mountNode}
onEscape={this.props.onEsc}
onDocumentClick={this.isHoverTrigger() ? undefined : this.onDocumentClick}
isHoverLayer={this.isHoverTrigger()}
onMount={() => this.setState({ isLayerMounted: true })}
onUnmount={() => this.setState({ isLayerMounted: false })}
>
<TetherBehavior
anchorRef={this.anchorRef.current}
arrowRef={this.arrowRef.current}
popperRef={this.popperRef.current}
// Remove the `ignoreBoundary` prop in the next major version
// and have it replaced with the TetherBehavior props overrides
popperOptions={{
...defaultPopperOptions,
...this.props.popperOptions,
}}
onPopperUpdate={this.onPopperUpdate}
placement={this.state.placement}
>
{this.props.focusLock &&
this.props.accessibilityType !== ACCESSIBILITY_TYPE.tooltip ? (
<FocusLock
disabled={!this.props.focusLock}
noFocusGuards={false}
// see popover-focus-loop.scenario.js for why hover cannot return focus
returnFocus={!this.isHoverTrigger() && this.props.returnFocus}
autoFocus={this.state.autoFocusAfterPositioning}
// Allow focus to escape when UI is within an iframe
crossFrame={false}
focusOptions={this.props.focusOptions}
>
{this.renderPopover(renderedContent)}
</FocusLock>
) : (
<MoveFocusInside
disabled={!this.props.autoFocus || !this.state.autoFocusAfterPositioning}
>
{this.renderPopover(renderedContent)}
</MoveFocusInside>
)}
</TetherBehavior>
</Layer>
);
} else {
rendered.push(<Hidden key="hidden-layer">{renderedContent}</Hidden>);
}
}
return rendered;
}