PhotoProvider.tsx 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899
  1. import React from 'react';
  2. import PhotoContext, {
  3. onShowType,
  4. addItemType,
  5. removeItemType,
  6. } from './photo-context';
  7. import PhotoSlider from './PhotoSlider';
  8. import { dataType, IPhotoProviderBase } from './types';
  9. export interface IPhotoProvider extends IPhotoProviderBase {
  10. children: React.ReactNode;
  11. }
  12. type PhotoProviderState = {
  13. images: dataType[];
  14. visible: boolean;
  15. index: number;
  16. onShow: onShowType;
  17. addItem: addItemType;
  18. removeItem: removeItemType;
  19. };
  20. export default class PhotoProvider extends React.Component<
  21. IPhotoProvider,
  22. PhotoProviderState
  23. > {
  24. constructor(props) {
  25. super(props);
  26. this.state = {
  27. images: [],
  28. visible: false,
  29. index: 0,
  30. addItem: this.handleAddItem,
  31. removeItem: this.handleRemoveItem,
  32. onShow: this.handleShow,
  33. };
  34. }
  35. handleAddItem = (key: string, src: string, intro: React.ReactNode) => {
  36. this.setState(prev => ({
  37. images: prev.images.concat({
  38. key,
  39. src,
  40. intro,
  41. }),
  42. }));
  43. };
  44. handleRemoveItem = (key: string) => {
  45. this.setState(({ images, index }) => {
  46. const nextImages = images.filter(item => item.key !== key);
  47. const nextEndIndex = nextImages.length - 1;
  48. return {
  49. images: nextImages,
  50. index: Math.min(nextEndIndex, index),
  51. };
  52. });
  53. };
  54. handleShow = (key: string) => {
  55. const { images } = this.state;
  56. this.setState({
  57. visible: true,
  58. index: images.findIndex(item => item.key === key),
  59. });
  60. };
  61. handleClose = () => {
  62. this.setState({
  63. visible: false,
  64. });
  65. };
  66. handleIndexChange = (index: number) => {
  67. this.setState({
  68. index,
  69. });
  70. };
  71. render() {
  72. const { children, ...restProps } = this.props;
  73. const { images, visible, index } = this.state;
  74. return (
  75. <PhotoContext.Provider value={this.state}>
  76. {children}
  77. <PhotoSlider
  78. images={images}
  79. visible={visible}
  80. index={index}
  81. onIndexChange={this.handleIndexChange}
  82. onClose={this.handleClose}
  83. {...restProps}
  84. />
  85. </PhotoContext.Provider>
  86. );
  87. }
  88. }