@@ -6,6 +6,10 @@ import Portal from '../Portal';
6
6
import { createChainedFunction } from '../utils/helpers' ;
7
7
import { useForkRef } from '../utils/reactHelpers' ;
8
8
9
+ /**
10
+ * Flips placement if in <body dir="rtl" />
11
+ * @param {string } placement
12
+ */
9
13
function flipPlacement ( placement ) {
10
14
const direction = ( typeof window !== 'undefined' && document . body . getAttribute ( 'dir' ) ) || 'ltr' ;
11
15
@@ -47,7 +51,7 @@ const Popper = React.forwardRef(function Popper(props, ref) {
47
51
keepMounted = false ,
48
52
modifiers,
49
53
open,
50
- placement : placementProps = 'bottom' ,
54
+ placement : initialPlacement = 'bottom' ,
51
55
popperOptions = defaultPopperOptions ,
52
56
popperRef : popperRefProp ,
53
57
transition = false ,
@@ -65,13 +69,20 @@ const Popper = React.forwardRef(function Popper(props, ref) {
65
69
React . useImperativeHandle ( popperRefProp , ( ) => popperRef . current , [ ] ) ;
66
70
67
71
const [ exited , setExited ] = React . useState ( ! open ) ;
68
- const [ placement , setPlacement ] = React . useState ( ) ;
72
+
73
+ const rtlPlacement = flipPlacement ( initialPlacement ) ;
74
+ /**
75
+ * placement initialized from prop but can change during lifetime if modifiers.flip.
76
+ * modifiers.flip is essentially a flip for controlled/uncontrolled behavior
77
+ */
78
+ const [ placement , setPlacement ] = React . useState ( rtlPlacement ) ;
79
+ if ( rtlPlacement !== placement ) {
80
+ setPlacement ( rtlPlacement ) ;
81
+ }
69
82
70
83
const handleOpen = React . useCallback ( ( ) => {
71
84
const handlePopperUpdate = data => {
72
- if ( data . placement !== placement ) {
73
- setPlacement ( data . placement ) ;
74
- }
85
+ setPlacement ( data . placement ) ;
75
86
} ;
76
87
77
88
const popperNode = tooltipRef . current ;
@@ -86,7 +97,7 @@ const Popper = React.forwardRef(function Popper(props, ref) {
86
97
}
87
98
88
99
const popper = new PopperJS ( getAnchorEl ( anchorEl ) , popperNode , {
89
- placement : flipPlacement ( placementProps ) ,
100
+ placement : rtlPlacement ,
90
101
...popperOptions ,
91
102
modifiers : {
92
103
...( disablePortal
@@ -102,11 +113,10 @@ const Popper = React.forwardRef(function Popper(props, ref) {
102
113
} ,
103
114
// We could have been using a custom modifier like react-popper is doing.
104
115
// But it seems this is the best public API for this use case.
105
- onCreate : createChainedFunction ( handlePopperUpdate , popperOptions . onCreate ) ,
106
116
onUpdate : createChainedFunction ( handlePopperUpdate , popperOptions . onUpdate ) ,
107
117
} ) ;
108
118
handlePopperRefRef . current ( popper ) ;
109
- } , [ anchorEl , disablePortal , modifiers , open , placement , placementProps , popperOptions ] ) ;
119
+ } , [ anchorEl , disablePortal , modifiers , open , rtlPlacement , popperOptions ] ) ;
110
120
111
121
const handleEnter = ( ) => {
112
122
setExited ( false ) ;
@@ -148,9 +158,7 @@ const Popper = React.forwardRef(function Popper(props, ref) {
148
158
return null ;
149
159
}
150
160
151
- const childProps = {
152
- placement : placement || flipPlacement ( placementProps ) ,
153
- } ;
161
+ const childProps = { placement } ;
154
162
155
163
if ( transition ) {
156
164
childProps . TransitionProps = {
0 commit comments