Proyectos de Subversion LeadersLinked - Antes de SPA

Rev

Autoría | Ultima modificación | Ver Log |

import React, { useState, useCallback, useEffect } from 'react'
import { useDropzone } from 'react-dropzone'
import { shareModalTypes } from '../../redux/share-modal/shareModal.types'
import IconButton from '@mui/material/IconButton'
import CloseIcon from '@mui/icons-material/Close'
import styled from 'styled-components'

import FormErrorFeedback from '../UI/FormErrorFeedback'

const DragAndDropContainer = styled.div`
  display: flex;
  flex-direction: column;
  align-items: center;
  padding: 2rem 0;
  border: 2px dashed #eee;
  border-radius: 2;
  background-color: #fafafa;
  color: #bdbdbd;
  outline: none;
  transition: border 0.24s ease-in-out;
  margin-top: 1rem;
  cursor: pointer;
`

const PreviewContainer = styled.div`
  display: flex;
  margin-top: 16px;
  position: relative;
  justify-content: center;

  img {
    width: auto;
    height: 100%;
    max-height: 200px;
    max-width: 350px;
    object-fit: contain;
  }
`

const CloseButton = styled(IconButton)`
  position: absolute;
  background-color: #000 !important;
  color: #fff;

  &:hover {
    color: #fff !important;
  }
`

const areEqual = (prevProps, nextProps) => {
  return prevProps.settedFile === nextProps.settedFile
}

const DropzoneComponent = ({
  modalType,
  onUploaded,
  settedFile,
  recomendationText,
}) => {
  const [errors, setErrors] = useState([])
  const [files, setFiles] = useState([])

  const acceptedMimeTypes = () => {
    switch (modalType) {
      case shareModalTypes.IMAGE:
        return 'image/jpeg, image/png, image/jpg'
      case shareModalTypes.FILE:
        return 'application/pdf, application/vnd.openxmlformats-officedocument.presentationml.presentation'
      case shareModalTypes.VIDEO:
        return 'video/mp4, video/mpeg, video/webm'
      case shareModalTypes.CHAT:
        return 'video/mp4, video/mpeg, video/webm, application/pdf, image/jpeg, image/png, image/jpg'
      default:
        return null
    }
  }

  const onDropRejected = useCallback((rejectedFiles) => {
    rejectedFiles.map((fileRejection) => {
      switch (fileRejection.errors[0].code) {
        case 'too-many-files':
          setErrors([...errors, 'solo puedes agregar 1 archivo'])
          break
        case 'file-invalid-type':
          setErrors([...errors, 'por favor seleccione un archivo valido'])
          break
        default:
          setErrors(errors)
          break
      }
    })
  }, [])

  const { getRootProps, getInputProps } = useDropzone({
    accept: acceptedMimeTypes(),
    multiple: false,
    onDrop: (acceptedFiles) => {
      onUploaded(acceptedFiles[0])
      setFiles(acceptedFiles.map((file) => file))
    },
    onDropRejected,
    onDropAccepted: () => {
      setErrors([])
    },
    maxFiles: 1,
  })

  const onDeleteFileHandler = (index) => {
    onUploaded('')
    setFiles([])
  }

  useEffect(() => {
    if (!settedFile) return
    setFiles([settedFile])
  }, [settedFile])

  const filePreviewTest = (file) => {
    switch (modalType) {
      case shareModalTypes.IMAGE:
        return <img src={URL.createObjectURL(file)} />
      case shareModalTypes.VIDEO:
        return (
          <video
            src={URL.createObjectURL(file)}
            width="400"
            height="300"
            controls
            autoPlay
            muted
          />
        )
      case shareModalTypes.CHAT:
        switch (file.type) {
          case 'video/mp4':
          case 'video/mpeg':
          case 'video/webm':
            return (
              <video
                src={URL.createObjectURL(file)}
                width="400"
                height="300"
                controls
                autoPlay
                muted
              />
            )
          case 'image/jpeg':
          case 'image/png':
          case 'image/jpg':
            return <img src={URL.createObjectURL(file)} />
          case 'application/pdf':
            return (
              <object
                data={URL.createObjectURL(file)}
                type="application/pdf"
                width="400"
                height="200"
              />
            )
          default:
            break
        }
        break
      case shareModalTypes.FILE:
        switch (file.type) {
          case 'application/vnd.openxmlformats-officedocument.presentationml.presentation':
            return (
              <iframe
                src={`https://view.officeapps.live.com/op/embed.aspx?src=${encodeURIComponent(
                  file
                )}`}
                width="100%"
                height="600px"
              />
            )
          case 'application/pdf':
            return (
              <object data={URL.createObjectURL(file)} type="application/pdf" />
            )
          default:
            break
        }
    }
  }

  return (
    <>
      {!files.length ? (
        <DragAndDropContainer {...getRootProps({ className: 'dropzone' })}>
          <input {...getInputProps()} />
          <p>Arrastra el archivo aqui, o haga click para seleccionar</p>
          {recomendationText}
        </DragAndDropContainer>
      ) : (
        <PreviewContainer>
          {files.map((file) => filePreviewTest(file))}
          <CloseButton className="close" onClick={() => onDeleteFileHandler()}>
            <CloseIcon />
          </CloseButton>
        </PreviewContainer>
      )}
      {errors.map((error, index) => (
        <FormErrorFeedback key={index}>{error}</FormErrorFeedback>
      ))}
    </>
  )
}

export default React.memo(DropzoneComponent, areEqual)