Untitled

mail@pastecode.io avatar
unknown
plain_text
3 years ago
9.5 kB
3
Indexable
Never
import React, { useState, useEffect, useContext, createContext, useMemo } from 'react';
import PropTypes from 'prop-types';
import { TopTab } from '../../navigation/utils';
import CustomTabBar from '../../navigation/CustomTabBar';

import { getAll as getPosts } from '../../apis/post';
import { getAll as getProducts } from '../../apis/product';
import { Promotions, Events, Products } from '..';
import { cloneWith, findIndex } from 'lodash';
import { useCallback } from 'react';
import { TAB_NAMES } from '../../utils';
import { FlatList, TouchableOpacity } from 'react-native';
import { FooterList } from '../Common';
import ProductCard from './ProductCard';

const MallContext = createContext();

const MallPromotion = () => {
  const [promotions, setPromotions] = useState({
    data: [],
    pagination: {},
    loading: false,
  });
  const mall = useContext(MallContext);

  useEffect(() => {
    fetchPromotions({ page: 1 });
  }, [mall]);

  const fetchPromotions = useCallback(
    ({ page }) => {
      setPromotions({ ...promotions, loading: true });
      const params = {
        filter: { 'mall.id': mall.id, type: 'promotion' },
        page: page,
      };
      getPosts(params)
        .then((response) => {
          setPromotions({
            loading: false,
            pagination: { currentPage: page, total: response.total },
            data: promotions.data.concat(response.results),
          });
        })
        .catch(() => {
          setPromotions({ ...promotions, loading: false });
        });
    },
    [promotions],
  );

  const onLoadMore = () => {
    const { data, pagination, loading } = promotions;
    if (data.length < pagination.total && !loading) {
      fetchPromotions({ page: pagination.currentPage + 1 });
    }
  };

  const onUpdatePromotion = useCallback(
    (promotion) => {
      const index = findIndex(promotions.data, (i) => i.id === promotion.id);
      if (index !== -1) {
        const tempData = [...promotions.data];
        tempData[index] = promotion;
        setPromotions({ ...promotions, data: tempData });
      }
    },
    [promotions],
  );

  return (
    <Promotions
      promotions={promotions.data}
      loading={promotions.loading}
      onLoadMore={onLoadMore}
      onUpdatePromotion={onUpdatePromotion}
    />
  );
};

const MallEvent = () => {
  const [events, setEvents] = useState({
    data: [],
    pagination: {},
    loading: false,
  });
  const mall = useContext(MallContext);

  useEffect(() => {
    fetchEvents({ page: 1 });
  }, []);

  const fetchEvents = useCallback(
    ({ page }) => {
      setEvents({ ...events, loading: true });
      const params = {
        filter: { 'mall.id': mall.id, type: 'event' },
        page: page,
      };
      getPosts(params)
        .then((response) => {
          setEvents({
            loading: false,
            pagination: { currentPage: page, total: response.total },
            data: events.data.concat(response.results),
          });
        })
        .catch(() => {
          setEvents({ ...events, loading: false });
        });
    },
    [events],
  );

  const onLoadMore = () => {
    const { data, pagination, loading } = events;
    if (data.length < pagination.total && !loading) {
      fetchEvents({ page: pagination.currentPage + 1 });
    }
  };

  const onUpdateEvent = useCallback(
    (event) => {
      const index = findIndex(events.data, (i) => i.id === event.id);
      if (index !== -1) {
        const tempData = [...events.data];
        tempData[index] = event;
        setEvents({ ...events, data: tempData });
      }
    },
    [events],
  );

  return (
    <Events
      events={events.data}
      loading={events.loading}
      onLoadMore={onLoadMore}
      onUpdateEvent={onUpdateEvent}
    />
  );
};

// const MallProducts = () => {
//   const mall = useContext(MallContext);

//   const [products, setProducts] = useState({
//     data: [],
//     pagination: {},
//     loading: false,
//   });

//   useEffect(() => {
//     fetchProducts({ page: 1 });
//   }, []);

//   const fetchProducts = useCallback(
//     ({ page }) => {
//       setProducts({ ...products, loading: true });
//       const params = { page, filter: { 'mall.id': mall.id } };
//       getProducts(params)
//         .then((response) => {
//           setProducts({
//             loading: false,
//             pagination: { currentPage: page, total: response.total },
//             data: products.data.concat(response.results),
//           });
//         })
//         .catch(() => {
//           setProducts({ ...products, loading: true });
//         });
//     },
//     [products],
//   );

//   const onUpdateProduct = useCallback(
//     (product) => {
//       const index = findIndex(products.data, (i) => i.id === product.id);
//       if (index !== -1) {
//         const data = [...products.data];
//         data[index] = product;
//         setProducts({ ...products, data });
//       }
//     },
//     [products],
//   );

//   const onLoadMore = () => {
//     console.log('loaddd')
//     const { data, pagination, loading } = products;
//     if (data.length < pagination.total && !loading) {
//       fetchProducts({ page: pagination.currentPage + 1 });
//     }
//   };

//   return (
//     <Products
//       products={products.data}
//       loading={products.loading}
//       // onLoadMore={onLoadMore}
//       onUpdateProduct={onUpdateProduct}
//     />
//   );
// };

const MallPost = ({ mall, renderHeader }) => {
  const [tab, setTab] = useState(0)
  const mall = useContext(MallContext);
  const [products, setProducts] = useState({
    data: [],
    pagination: {},
    loading: false,
  });

  useEffect(() => {
    fetchProducts({ page: 1 });
  }, []);

  const fetchProducts = useCallback(
    ({ page }) => {
      setProducts({ ...products, loading: true });
      const params = { page, filter: { 'mall.id': mall.id } };
      getProducts(params)
        .then((response) => {
          setProducts({
            loading: false,
            pagination: { currentPage: page, total: response.total },
            data: products.data.concat(response.results),
          });
        })
        .catch(() => {
          setProducts({ ...products, loading: true });
        });
    },
    [products],
  );

  const onUpdateProduct = useCallback(
    (product) => {
      const index = findIndex(products.data, (i) => i.id === product.id);
      if (index !== -1) {
        const data = [...products.data];
        data[index] = product;
        setProducts({ ...products, data });
      }
    },
    [products],
  );

  const onLoadMore = () => {
    const { data, pagination, loading } = products;
    if (data.length < pagination.total && !loading) {
      fetchProducts({ page: pagination.currentPage + 1 });
    }
  };

  const renderHeaderFlatlist = () => {
    const TobTab = useMemo(() => {
      return ['MallDetailPromotion', 'MallDetailEvent', 'MallDetailProduct']
    }, [])

    const pressButton = useCallback((index) => {
      setTab(index)
    })

    const renderButton = (item, index) => {
      // Tu design lai cho giong top tab cua navigation nha
      return (
        <TouchableOpacity onPress={() => pressButton(index)}>
          <Text>{item}</Text>
        </TouchableOpacity>
      )
    }
    return (
      <View>
        { renderHeader()}
        <View>
          {TobTab.map(renderButton)}
        </View>
      </View>
    )
  }
  const renderFooter = () => {
    return (
      <>
        {tab === 0 && MallPromotion()}
        {tab === 1 && MallEvent()}
        {tab === 2 && (<FooterList loading={products?.loading} />)}
      </>
    )
  }

  const renderItem = () => {
    return (
      <ProductCard product={item} onUpdateProduct={onUpdateProduct} />
    )
  }

  const renderEmpty = () => {
    if (tab !== 2) {
      return null
    }
    return (
      <>
        {!products?.loading && <EmptyList message={'No products available'} />}
      </>
    )
  }

  return (
    <MallContext.Provider value={mall}>
      <FlatList
        data={tab === 2 ? products?.data || [] : []}
        numColumns={2}
        renderHeader={renderHeaderFlatlist}
        onEndReachedThreshold={0.2}
        onEndReached={onLoadMore}
        keyExtractor={(item, index) => index.toString()}
        ListFooterComponent={renderFooter}
        renderItem={renderItem}
        ListEmptyComponent={renderEmpty}
      />
      {/* <TopTab.Navigator tabBar={(props) => <CustomTabBar {...props} />} lazy>
        <TopTab.Screen
          name="MallDetailPromotion"
          component={MallPromotion}
          options={{ title: TAB_NAMES.PROMOTION }}
        />
        <TopTab.Screen
          name="MallDetailEvent"
          component={MallEvent}
          options={{ title: TAB_NAMES.EVENT }}
        />
        <TopTab.Screen
          name="MallDetailProduct"
          component={MallProducts}
          options={{ title: TAB_NAMES.PRODUCT }}
        />
      </TopTab.Navigator> */}
    </MallContext.Provider>
  );
};

MallPost.propTypes = {
  mall: PropTypes.object,
};

MallPost.defaultProps = {};

export default MallPost;