import React, {Component} from "react";
import {findDOMNode} from "react-dom";
import {connect} from "react-redux";
import classnames from "classnames";
import {
  mobileCheck,
  sortCallParticipantsBy
} from "../utils/helpers";

//strings
import {CHAT_CALL_BOX_FULL_SCREEN} from "../constants/callModes";

//actions

//components
import {getName} from "./_component/contactList";
import Container from "../../../Talk-ui-kit/src/container";
import {MdMicOff} from "react-icons/md";

//styling
import style from "../../styles/app/CallBoxSceneGroupVideoThumbnail.scss";
import CallBoxReconnecting from "./CallBoxReconnecting";

//statics

//functions

@connect(store => {
  return {
    chatCallParticipantList: sortCallParticipantsBy(store.chatCallParticipantList.participants, "id"),
    chatCallGroupSettingsShowing: store.chatCallGroupSettingsShowing,
    chatCallGroupVideoViewMode: store.chatCallGroupVideoViewMode
  };
})
export default class CallBoxSceneGroupVideoThumbnail extends Component {

  constructor(props) {
    super(props);
    this.state = {
      sceneParticipant: null
    }
    this.scroller = {
      isDown: false,
      startX: null,
      scrollLeft: null,
      participantMouseDown: null
    };
    this.onScrollerMouseDown = this.onScrollerMouseDown.bind(this);
    this.onScrollerMouseLeaveUp = this.onScrollerMouseLeaveUp.bind(this);
    this.onScrollerMouseMove = this.onScrollerMouseMove.bind(this);
    this.onParticipantMouseDown = this.onParticipantMouseDown.bind(this);
    this.scrollerRef = React.createRef();
  }

  componentDidUpdate(prevProps, prevState, snapshot) {
    let {sceneParticipant} = prevState;
    let {sceneParticipant: nowSceneParticipant} = this.state;
    const {
      isScreenShare,
      traverseOverContactForInjecting,
      participant,
      chatCallParticipantList,
      injectVideo,
      isVideoCall,
      chatCallStatus
    } = this.props;

    const {call} = chatCallStatus;
    const {uiElements} = call;
    sceneParticipant = sceneParticipant || participant;


    if (isScreenShare) {
      const tag = document.getElementById('video-screenShare');
      return setTimeout(() => {
        injectVideo(tag, "screenShare");
      }, 1000);
    }

    const goForInjectingCondition = ((sceneParticipant && nowSceneParticipant) && (sceneParticipant.id !== nowSceneParticipant.id)) || !sceneParticipant;
    if (goForInjectingCondition) {
      nowSceneParticipant = nowSceneParticipant && nowSceneParticipant.id ? nowSceneParticipant : chatCallParticipantList && chatCallParticipantList[0];
      if (!nowSceneParticipant) {
        return;
      }
      setTimeout(() => {
        const tag = document.getElementById(`video-${nowSceneParticipant.id}`);

        if (tag) {
          tag.innerHTML = "";
          traverseOverContactForInjecting();
        }
      }, 500);
    }
  }

  componentDidMount() {
    const {
      isScreenShare,
      injectVideo
    } = this.props;
    if (isScreenShare) {
      const tag = document.getElementById('video-screenShare');

      if (tag) {
        setTimeout(() => {
          injectVideo(tag, "screenShare");
        }, 1000);
      }
    }

  }

  componentWillUnmount() {
    this.props.resetMediaSourceLocation();
  }

  onParticipantClick(participant, e) {
    e.stopPropagation();
    const slider = findDOMNode(this.scrollerRef.current);
    if (slider.scrollLeft !== this.scroller.participantMouseDown) {
      return
    }
    this.props.resetMediaSourceLocation();
    this.setState({
      sceneParticipant: participant
    });
  }

  onScrollerMouseDown(e) {
    e.stopPropagation();
    e.preventDefault();
    const slider = e.currentTarget;
    this.scroller.isDown = true
    this.scroller.startX = e.pageX - slider.offsetLeft;
    this.scroller.scrollLeft = slider.scrollLeft;
  }

  onParticipantMouseDown() {
    this.scroller.participantMouseDown = findDOMNode(this.scrollerRef.current).scrollLeft;
  }

  onScrollerMouseLeaveUp(e) {
    e.stopPropagation();
    e.preventDefault();
    this.scroller.isDown = false;
  }

  onScrollerMouseMove(e) {
    e.stopPropagation();
    e.preventDefault();
    const slider = e.currentTarget;
    if (!this.scroller.isDown) return;
    e.preventDefault();
    const x = e.pageX - slider.offsetLeft;
    const walk = (x - this.scroller.startX) * 3; //scroll-fast
    slider.scrollLeft = this.scroller.scrollLeft - walk;
  }

  render() {
    const {
      chatCallStatus,
      chatCallParticipantList,
      participant,
      chatCallBoxShowing,
      isScreenShare
    } = this.props;
    let {sceneParticipant} = this.state;
    const fullScreenCondition = chatCallBoxShowing.showing === CHAT_CALL_BOX_FULL_SCREEN;
    const {call} = chatCallStatus;
    const isMobile = mobileCheck();
    const {uiElements} = call;
    sceneParticipant = sceneParticipant || participant;
    sceneParticipant = sceneParticipant && sceneParticipant.id ? sceneParticipant : chatCallParticipantList.find(participant => participant.id === sceneParticipant);
    if (uiElements) {
      const selectOnePersonForBeingSceneParticipant = !sceneParticipant || (sceneParticipant && !uiElements[sceneParticipant.id]?.video);
      if (selectOnePersonForBeingSceneParticipant) {
        sceneParticipant = chatCallParticipantList.find(participant => uiElements[participant.id]?.video);
      }
    }

    const filterParticipants = chatCallParticipantList.filter(participant => {
      return (uiElements[participant.id]?.video && !participant.videoMute) && (isScreenShare || participant.id !== sceneParticipant?.id);
    });

    const classNames = classnames({
      [style.CallBoxSceneGroupVideoThumbnail]: true,
    });

    const listClassNames = classnames({
      [style.CallBoxSceneGroupVideoThumbnail__List]: true,
      [style["CallBoxSceneGroupVideoThumbnail__List--mobile"]]: mobileCheck(),
      [style["CallBoxSceneGroupVideoThumbnail__List--fullScreen"]]: fullScreenCondition
    })

    const sceneClassNames = classnames({
      [style.CallBoxSceneGroupVideoThumbnail__Scene]: true,
      [style["CallBoxSceneGroupVideoThumbnail__Scene--screenShare"]]: isScreenShare
    });

    const listScrollerClassNames = classnames({
      [style.CallBoxSceneGroupVideoThumbnail__ListScroller]: true,
      [style["CallBoxSceneGroupVideoThumbnail__ListScroller--mobile"]]: isMobile
    });

    const MuteContainer = ({participant}) => {
      if (!participant?.mute) {
        return;
      }
      return <Container center>
        <MdMicOff size={style.iconSizeXs}
                  color={style.colorAccent}
                  style={{margin: "3px 4px"}}/>
      </Container>
    }

    return <Container className={classNames}>
      <Container className={sceneClassNames}>
        {!isScreenShare &&
        <>
          <MuteContainer participant={sceneParticipant}/>
          <CallBoxReconnecting participant={sceneParticipant} className={style.CallBoxSceneGroupVideoThumbnail__ReconnectingContainer} isVideo/>
        </>
        }
        <Container
          id={isScreenShare ? "video-screenShare" : `video-${sceneParticipant?.id || "video-scene"}`}
          className={style.CallBoxSceneGroupVideoThumbnail__CamVideoContainer}/>
      </Container>
      <Container className={listClassNames}>
        <Container className={style.CallBoxSceneGroupVideoThumbnail__ListContainer}>
          <Container className={listScrollerClassNames}
                     ref={this.scrollerRef}
                     onMouseDown={!isMobile && this.onScrollerMouseDown}
                     onMouseLeave={!isMobile && this.onScrollerMouseLeaveUp}
                     onMouseUp={!isMobile && this.onScrollerMouseLeaveUp}
                     onMouseMove={!isMobile && this.onScrollerMouseMove}>
            {filterParticipants.map((participant, index) =>
              <Container className={style.CallBoxSceneGroupVideoThumbnail__ListItem}
                         title={getName(participant)}
                         key={participant.id}
                         onMouseDown={this.onParticipantMouseDown}
                         onClick={!isScreenShare && this.onParticipantClick.bind(this, participant)}>
                <MuteContainer participant={participant}/>
                <CallBoxReconnecting participant={participant} className={style.CallBoxSceneGroupVideoThumbnail__ReconnectingContainer} isVideo/>
                <Container id={`video-${participant.id}`}
                           className={style.CallBoxSceneGroupVideoThumbnail__CamVideoContainer}/>

              </Container>
            )}
          </Container>
        </Container>

      </Container>
    </Container>
  }
}