@@ -42,6 +42,7 @@ export type PopperProps = {
4242
4343type PopperState = {
4444 data : ?Data ,
45+ placement : ?Placement ,
4546} ;
4647
4748const initialStyle = {
@@ -64,6 +65,7 @@ export class InnerPopper extends React.Component<PopperProps, PopperState> {
6465
6566 state = {
6667 data : undefined ,
68+ placement : undefined ,
6769 } ;
6870
6971 popperInstance : ?PopperJS$Instance ;
@@ -91,7 +93,11 @@ export class InnerPopper extends React.Component<PopperProps, PopperState> {
9193 enabled : true ,
9294 order : 900 ,
9395 fn : ( data : Object ) => {
94- this . setState ( { data } ) ;
96+ const { placement } = data ;
97+ this . setState (
98+ { data, placement } ,
99+ placement !== this . state . placement ? this . scheduleUpdate : undefined
100+ ) ;
95101 return data ;
96102 } ,
97103 } ;
@@ -120,7 +126,7 @@ export class InnerPopper extends React.Component<PopperProps, PopperState> {
120126 } ;
121127
122128 getPopperPlacement = ( ) =>
123- ! this . state . data ? undefined : this . state . data . placement ;
129+ ! this . state . data ? undefined : this . state . placement ;
124130
125131 getArrowStyle = ( ) =>
126132 ! this . arrowNode || ! this . state . data
@@ -158,7 +164,7 @@ export class InnerPopper extends React.Component<PopperProps, PopperState> {
158164 }
159165 } ;
160166
161- componentDidUpdate ( prevProps : PopperProps ) {
167+ componentDidUpdate ( prevProps : PopperProps , prevState : PopperState ) {
162168 // If the Popper.js options have changed, update the instance (destroy + create)
163169 if (
164170 this . props . placement !== prevProps . placement ||
@@ -167,6 +173,15 @@ export class InnerPopper extends React.Component<PopperProps, PopperState> {
167173 this . props . positionFixed !== prevProps . positionFixed
168174 ) {
169175 this . updatePopperInstance ( ) ;
176+ return ;
177+ }
178+
179+ // A placement difference in state means popper determined a new placement
180+ // apart from the props value. By the time the popper element is rendered with
181+ // the new position Popper has already measured it, if the place change triggers
182+ // a size change it will result in a misaligned popper. So we schedule an update to be sure.
183+ if ( prevState . placement !== this . state . placement ) {
184+ this . scheduleUpdate ( ) ;
170185 }
171186 }
172187
0 commit comments