5
5
PositioningProps ,
6
6
PositioningVirtualElement ,
7
7
PositioningImperativeRef ,
8
+ type PositioningRect ,
8
9
} from '@fluentui/react-positioning' ;
9
- import { useMergedRefs } from '@fluentui/react-utilities' ;
10
+ import { useMergedRefs , useIsomorphicLayoutEffect } from '@fluentui/react-utilities' ;
10
11
import { useFluent_unstable as useFluent } from '@fluentui/react-shared-contexts' ;
11
12
import { Steps , StoryWright } from 'storywright' ;
12
13
@@ -814,11 +815,7 @@ const PositioningEndEvent = () => {
814
815
} ;
815
816
816
817
const TargetDisplayNone = ( ) => {
817
- const positioningRef = React . useRef < PositioningImperativeRef > ( null ) ;
818
- const { targetRef, containerRef } = usePositioning ( {
819
- positioningRef,
820
- } ) ;
821
-
818
+ const { targetRef, containerRef } = usePositioning ( { } ) ;
822
819
const [ visible , setVisible ] = React . useState ( true ) ;
823
820
824
821
return (
@@ -939,6 +936,95 @@ const ShiftToCoverTargetAsyncContent = () => {
939
936
) ;
940
937
} ;
941
938
939
+ const BoundaryRect = ( ) => {
940
+ const rectHostRef = React . useRef < HTMLDivElement > ( null ) ;
941
+
942
+ const boundaryRect = React . useMemo < PositioningRect > (
943
+ ( ) => ( {
944
+ width : 700 ,
945
+ height : 700 ,
946
+ x : 70 ,
947
+ y : 70 ,
948
+ } ) ,
949
+ [ ] ,
950
+ ) ;
951
+ const { targetRef, containerRef } = usePositioning ( {
952
+ overflowBoundary : boundaryRect ,
953
+
954
+ position : 'below' ,
955
+ align : 'end' ,
956
+ } ) ;
957
+
958
+ useIsomorphicLayoutEffect ( ( ) => {
959
+ const rectEl = document . createElement ( 'div' ) ;
960
+
961
+ Object . assign ( rectEl . style , {
962
+ position : 'fixed' ,
963
+ border : '4px solid orange' ,
964
+ boxSizing : 'border-box' ,
965
+
966
+ left : `${ boundaryRect . x } px` ,
967
+ top : `${ boundaryRect . y } px` ,
968
+ width : `${ boundaryRect . width } px` ,
969
+ height : `${ boundaryRect . height } px` ,
970
+
971
+ zIndex : 1 ,
972
+ } ) ;
973
+
974
+ rectHostRef . current ?. append ( rectEl ) ;
975
+
976
+ return ( ) => {
977
+ rectEl . remove ( ) ;
978
+ } ;
979
+ } , [ boundaryRect ] ) ;
980
+
981
+ return (
982
+ < >
983
+ < div ref = { rectHostRef } />
984
+ < div
985
+ style = { {
986
+ display : 'flex' ,
987
+ width : 800 ,
988
+ height : 800 ,
989
+ border : '4px dashed green' ,
990
+ padding : 50 ,
991
+
992
+ position : 'absolute' ,
993
+ left : 10 ,
994
+ top : 10 ,
995
+ } }
996
+ >
997
+ < div
998
+ style = { {
999
+ padding : 20 ,
1000
+ backgroundColor : 'lightgray' ,
1001
+ fontSize : 20 ,
1002
+ display : 'flex' ,
1003
+ height : 'fit-content' ,
1004
+ width : '100%' ,
1005
+ } }
1006
+ ref = { targetRef }
1007
+ >
1008
+ Hello world
1009
+ </ div >
1010
+ </ div >
1011
+ < div
1012
+ ref = { containerRef }
1013
+ style = { { border : '2px solid blue' , padding : 10 , backgroundColor : 'white' , boxSizing : 'border-box' , zIndex : 2 } }
1014
+ >
1015
+ < ul >
1016
+ < li >
1017
+ SHOULD BE below gray box as it's a < code > target</ code >
1018
+ </ li >
1019
+ < li >
1020
+ SHOULD BE inside an orange box as it's a < code > overflowBoundary</ code >
1021
+ </ li >
1022
+ </ ul >
1023
+ </ div >
1024
+ </ >
1025
+ ) ;
1026
+ } ;
1027
+
942
1028
export default {
943
1029
title : 'Positioning' ,
944
1030
@@ -960,6 +1046,9 @@ export default {
960
1046
] ,
961
1047
} satisfies Meta < 'div' > ;
962
1048
1049
+ export const _BoundaryRect = ( ) => < BoundaryRect /> ;
1050
+ _BoundaryRect . storyName = 'using boundary rect' ;
1051
+
963
1052
export const _PositionAndAlignProps = ( ) => < PositionAndAlignProps /> ;
964
1053
_PositionAndAlignProps . storyName = 'position and align props' ;
965
1054
0 commit comments