Files
watchparty/app/src/Thread.js
T

145 lines
5.5 KiB
JavaScript

/************************************************************************
Copyright (C) Ayushya Amitabh - All Rights Reserved
Unauthorized copying of this file, via any medium is strictly prohibited
Proprietary and confidential
Written by Ayushya Amitabh <admin@chromewatchparty.com>, 2020
https://www.chromewatchparty.com/copyright
=========================================================================
ALL CONTENT ON IN WATCH PARTY'S CHROME EXTENSION APP, UNLESS OTHERWISE
CITED ARE THE SOLE INTELECTUAL PROPERTY OF AYUSHYA AMITABH, AND MAY NOT BE
COPIED, EDITED, OR REPRODUCED WITHOUT PERMISSION.
Netflix logo is a trademark and intellectual property of Netflix, Inc.
Disney+ logo is a trademark and intellectual property of The Walt Disney Company
Prime logo is a trademark and intellectual property of Amazon.com, Inc.
YouTube logo is a trademark and intellectual property of Google, Inc.
Hulu logo is a trademark and intellectual property of Hulu, LLC.
HBO Now and HBO Max logos are trademark and intellectual property of WarnerMedia Direct,LLC.
************************************************************************/
import React, { Component } from 'react';
import { Typography, IconButton, Paper, TextField, InputAdornment } from '@material-ui/core';
import { Reply, Send } from '@material-ui/icons';
import './Thread.css';
import { LocalData, webhookFetcher } from './Api';
export default class Thread extends Component {
constructor(props) {
super(props);
this.getReplyMessage = this.getReplyMessage.bind(this);
this.getMessageTextOrImage = this.getMessageTextOrImage.bind(this);
}
scrollToMessage(id) {
const pcc = document.querySelector('.thread-wrapper');
const msg = document.getElementById(id);
pcc.scrollTop = msg.offsetTop - pcc.offsetTop;
msg.classList.add('highlight');
setTimeout(() => msg.classList.remove('highlight'), 500);
}
handleInteractiveMessageCall(msg) {
const thanksElement = document.createElement('div');
thanksElement.innerText = 'THANK YOU FOR THE FEEDBACK';
thanksElement.className = 'thread-interactive-thankyou';
if (msg.uid === '<system>') {
if (msg.endpoint) {
var bodyData = {
question: msg.text,
};
if (msg.type === 'interactive/text') {
const answerElement = document.getElementById(`reply-${msg.id}`);
bodyData.answer = answerElement ? answerElement.value : 'ANSWER_ELEM_NOT_FOUND';
answerElement.disabled = true;
answerElement.parentElement.parentElement.parentElement.firstElementChild.remove();
answerElement.parentElement.replaceWith(thanksElement);
}
webhookFetcher({
endpoint: msg.endpoint,
body: JSON.stringify(bodyData),
});
}
}
}
getItemClassNames(uid, userUid, msgIdx) {
const lastUid = msgIdx >= 1 ? this.props.messages[msgIdx - 1].uid : '';
return `thread-item ${uid === userUid ? 'my-message' : ''} ${
uid === '<system>' ? 'system-message' : ''
} ${lastUid === uid ? 'continued-message' : ''}`;
}
getMessageTextOrImage(msg) {
if (msg.type === 'giphy') {
return <img alt="gif" src={msg.text} />;
}
if (msg.type === 'interactive/text') {
return (
<Paper elevation={0} className="thread-interactive-text">
<Typography className="thread-interactive-question" variant="overline">
{msg.text}
</Typography>
<TextField
className="thread-interactive-answer addFocus"
size="small"
id={`reply-${msg.id}`}
multiline
variant="outlined"
color="secondary"
InputProps={{
endAdornment: (
<InputAdornment position="end">
<IconButton onClick={() => this.handleInteractiveMessageCall(msg)}>
<Send />
</IconButton>
</InputAdornment>
),
}}
rowsMax={2}
/>
</Paper>
);
}
return <p>{msg.text}</p>;
}
getTimeString(time) {
return new Date(time.seconds * 1000).toLocaleTimeString();
}
getReplyMessage(rT, messages) {
if (rT !== undefined && rT !== null) {
const replyMessage = messages.filter((m) => m.id === rT)[0];
return (
<div className="thread-reply" onClick={() => this.scrollToMessage(replyMessage.id)}>
<p className="thread-reply-name">Reply to {replyMessage.name}:</p>
{this.getMessageTextOrImage(replyMessage)}
</div>
);
}
return null;
}
render() {
const { messages, setReplyTo } = this.props;
const { userUid } = LocalData();
return (
<div className="thread-container">
{messages.map((msg, msgIdx) => (
<div
id={msg.id}
key={`msg-${msgIdx}`}
className={this.getItemClassNames(msg.uid, userUid, msgIdx)}
>
<div className="thread-name">{msg.name}</div>
{this.getReplyMessage(msg.replyTo, messages)}
<div className="thread-message">
<div className="thread-overline">
<span>{this.getTimeString(msg.time)}</span>
<div className="thread-reply-icon">
<IconButton onClick={() => setReplyTo(msg)}>
<Reply />
</IconButton>
</div>
</div>
{this.getMessageTextOrImage(msg)}
</div>
</div>
))}
</div>
);
}
}