SlideDown.tsx 1.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051
  1. import React, { CSSProperties, FC } from 'react';
  2. import Transition from 'react-transition-group/Transition';
  3. interface Style {
  4. transition?: string;
  5. overflow?: string;
  6. }
  7. // When animating using max-height we need to use a static value.
  8. // If this is not enough, pass in <SlideDown maxHeight="....
  9. const defaultMaxHeight = '200px';
  10. const defaultDuration = 200;
  11. export const defaultStyle: Style = {
  12. transition: `max-height ${defaultDuration}ms ease-in-out`,
  13. overflow: 'hidden',
  14. };
  15. export interface Props {
  16. children: React.ReactNode;
  17. in: boolean;
  18. maxHeight?: number;
  19. style?: CSSProperties;
  20. }
  21. export const SlideDown: FC<Props> = ({ children, in: inProp, maxHeight = defaultMaxHeight, style = defaultStyle }) => {
  22. // There are 4 main states a Transition can be in:
  23. // ENTERING, ENTERED, EXITING, EXITED
  24. // https://reactcommunity.or[g/react-transition-group/
  25. const transitionStyles: { [str: string]: CSSProperties } = {
  26. exited: { maxHeight: 0 },
  27. entering: { maxHeight: maxHeight },
  28. entered: { maxHeight: 'unset', overflow: 'visible' },
  29. exiting: { maxHeight: 0 },
  30. };
  31. return (
  32. <Transition in={inProp} timeout={defaultDuration}>
  33. {state => (
  34. <div
  35. style={{
  36. ...style,
  37. ...transitionStyles[state],
  38. }}
  39. >
  40. {children}
  41. </div>
  42. )}
  43. </Transition>
  44. );
  45. };