Skip to content

Commit

Permalink
fix(Affix): fix unupdated position after window size change (#2256)
Browse files Browse the repository at this point in the history
  • Loading branch information
simonguo committed Dec 24, 2021
1 parent 3ff238c commit 61c7b27
Show file tree
Hide file tree
Showing 4 changed files with 56 additions and 2 deletions.
8 changes: 6 additions & 2 deletions src/Affix/Affix.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import React, { useCallback, useEffect, useRef, useState } from 'react';
import PropTypes from 'prop-types';
import getOffset from 'dom-lib/getOffset';
import { Offset, RsRefForwardingComponent, WithAsProps } from '../@types/common';
import { mergeRefs, useClassNames, useElementResize, useEventListener } from '../utils';
import { mergeRefs, useClassNames, useElementResize, useEventListener, useMount } from '../utils';

export interface AffixProps extends WithAsProps {
/** Distance from top */
Expand All @@ -20,6 +20,7 @@ export interface AffixProps extends WithAsProps {
*/
function useOffset(mountRef: React.RefObject<HTMLDivElement>) {
const [offset, setOffset] = useState<Offset | null>(null);

const updateOffset = useCallback(() => {
setOffset(getOffset(mountRef.current!));
}, [mountRef]);
Expand All @@ -28,7 +29,10 @@ function useOffset(mountRef: React.RefObject<HTMLDivElement>) {
useElementResize(() => mountRef.current!, updateOffset);

// Initialize after the first render
useEffect(updateOffset, [updateOffset]);
useMount(updateOffset);

// Update after window size changes
useEventListener(window, 'resize', updateOffset, false);

return offset;
}
Expand Down
1 change: 1 addition & 0 deletions src/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,3 +42,4 @@ export { default as useUpdatedRef } from './useUpdatedRef';
export { default as useWillUnmount } from './useWillUnmount';
export { default as useUpdateEffect } from './useUpdateEffect';
export { default as useIsMounted } from './useIsMounted';
export { default as useMount } from './useMount';
36 changes: 36 additions & 0 deletions src/utils/test/useMountSpec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
import { renderHook } from '@testing-library/react-hooks/dom';
import useMount from '../useMount';

describe('[utils] useMount', () => {
it('should call provided callback on mount', () => {
const callbackSpy = sinon.spy();

renderHook(() => useMount(callbackSpy));

assert.equal(callbackSpy.callCount, 1);
});

it('should not call provided callback on unmount', () => {
const callbackSpy = sinon.spy();

const { unmount } = renderHook(() => useMount(callbackSpy));

assert.equal(callbackSpy.callCount, 1);

unmount();

assert.equal(callbackSpy.callCount, 1);
});

it('should not call provided callback on rerender', () => {
const callbackSpy = sinon.spy();

const { rerender } = renderHook(() => useMount(callbackSpy));

assert.equal(callbackSpy.callCount, 1);

rerender();

assert.equal(callbackSpy.callCount, 1);
});
});
13 changes: 13 additions & 0 deletions src/utils/useMount.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import { useEffect, useRef } from 'react';

const useMount = (callback: () => void) => {
const mountRef = useRef(callback);

mountRef.current = callback;

useEffect(() => {
mountRef.current?.();
}, []);
};

export default useMount;

1 comment on commit 61c7b27

@vercel
Copy link

@vercel vercel bot commented on 61c7b27 Dec 24, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please sign in to comment.