aboutsummaryrefslogblamecommitdiff
path: root/src/Chat.js
blob: 84e1193d4a8844ac6c66db979bd65584a4f87b84 (plain) (tree)














































                                                                                
         



























                                                                            


                             





                                                















































































                                                                                        
import React, { Component } from "react";
import { w3cwebsocket as W3CWebSocket } from "websocket";
import { Header, List, Input } from "semantic-ui-react";
import Moment from "react-moment";
import "moment/locale/es";

class Chat extends Component {
  constructor(props) {
    super(props);
    this.state = {
      chat: [],
      chatMessage: "",
      chatUserCount: 0,
      isChatOnline: false
    };
    this.client = {};
    this.chatColors = [
      "grey",
      "red",
      "pink",
      "orange",
      "yellow",
      "green",
      "teal",
      "blue",
      "purple",
      "black"
    ];
    this.handleOnChange = this.handleOnChange.bind(this);
    this.sendMessage = this.sendMessage.bind(this);
  }

  handleOnChange(e, data) {
    this.setState({ chatMessage: data.value });
  }

  translateColon(msg) {
    return msg ? msg.replace(/%3A/g, ":") : "";
  }

  addMessage(message, color, own = false, sender = "") {
    var ts = new Date();
    this.setState(
      prevState => ({
        chat: [
          ...prevState.chat,
          { content: message, color: color, own, timestamp: ts, author: sender }
        ]
      }),
      () => {
        let chatContainer = document.getElementById("chatContainer");
        if (chatContainer != null) {
          chatContainer.scrollTop = chatContainer.scrollHeight;
        }
      }
    );
  }

  componentWillMount() {
    this.client = new W3CWebSocket(
      "wss://radio.bienvenidoainternet.org/daemon/"
    );
    this.client.onopen = () => {
      this.setState({ isChatOnline: true });
    };
    this.client.onmessage = message => {
      this.processChatMessage(message.data);
    };
    this.client.onerror = () => {
      this.setState({ isChatOnline: false });
      this.addMessage("Ha ocurrido un error conectándose al chat.", "red");
    };
  }

  sendMessage() {
    const { chatMessage } = this.state;
    if (chatMessage === "") {
      return;
    }
    this.client.send("MSG:1:" + chatMessage);
    this.addMessage(chatMessage, "black", true);
    this.setState({ chatMessage: "" });
  }

  processChatMessage(line) {
    const args = line.split(":");
    switch (args[0]) {
      case "MSG":
        this.addMessage(this.translateColon(args[2]), this.chatColors[args[1]]);
        break;
      case "FMSG":
        this.addMessage(
          this.translateColon(args[3]),
          this.chatColors[args[2]],
          false,
          args[1]
        );
        break;
      case "WELCOME":
        this.addMessage("Conectado al chat, " + args[1], "green");
        break;
      case "COUNT":
        this.setState({ chatUserCount: args[1] });
        break;
      case "FLOOD":
        this.addMessage(
          "Error: Estas enviando mensajes demasido rápido!",
          "red"
        );
        break;
      default:
        console.error("[Chat] Unsupported command " + args[0]);
        break;
    }
  }

  render() {
    const { chat, chatMessage, chatUserCount, isChatOnline } = this.state;
    return (
      <>
        <Header as="h3">
          Chat
          <Header.Subheader>{`Usuarios en el chat: ${chatUserCount}`}</Header.Subheader>
        </Header>
        <div id="chatContainer">
          <List>
            {chat.map((message, i) => (
              <List.Item key={i}>
                [<Moment format="HH:mm:ss" date={message.timestamp} />]{" "}
                <span className={`ui text ${message.color}`}>
                  {message.content}
                </span>
              </List.Item>
            ))}
          </List>
        </div>
        <Input
          fluid
          size="mini"
          action={{
            content: "Enviar",
            onClick: () => {
              this.sendMessage();
            },
            disabled: !isChatOnline
          }}
          placeholder=""
          value={chatMessage}
          onChange={this.handleOnChange}
          style={{ marginTop: "0.75em" }}
          maxLength={128}
          onKeyUp={e => {
            let char = e.which || e.keyCode;
            if (char === 13) {
              this.sendMessage();
            }
          }}
          disabled={!isChatOnline}
        />
      </>
    );
  }
}

export default Chat;