2
0

🚀 Init preview and typebot cotext in editor

This commit is contained in:
Baptiste Arnaud
2021-12-22 14:59:07 +01:00
parent a54e42f255
commit b7cdc0d14a
87 changed files with 4431 additions and 735 deletions

View File

@ -0,0 +1,20 @@
import React from 'react'
import { CSSTransition } from 'react-transition-group'
interface Props {
message: string
}
export const GuestBubble = ({ message }: Props): JSX.Element => {
return (
<CSSTransition classNames="bubble" timeout={1000}>
<div className="flex justify-end mb-2 items-center">
<div className="flex items-end w-11/12 lg:w-4/6 justify-end">
<div className="inline-flex px-4 py-2 rounded-lg mr-2 whitespace-pre-wrap max-w-full typebot-guest-bubble">
{message}
</div>
</div>
</div>
</CSSTransition>
)
}

View File

@ -0,0 +1,78 @@
import React, { useEffect, useRef, useState } from 'react'
import { useHostAvatars } from '../../../../contexts/HostAvatarsContext'
import { StepType, TextStep } from '../../../../models'
import { TypingContent } from './TypingContent'
type HostMessageBubbleProps = {
step: TextStep
onTransitionEnd: () => void
}
export const showAnimationDuration = 400
export const mediaLoadingFallbackTimeout = 5000
export const HostMessageBubble = ({
step,
onTransitionEnd,
}: HostMessageBubbleProps) => {
const { updateLastAvatarOffset } = useHostAvatars()
const messageContainer = useRef<HTMLDivElement | null>(null)
const [isTyping, setIsTyping] = useState(true)
useEffect(() => {
const wordCount = step.content.plainText.match(/(\w+)/g)?.length ?? 0
const typedWordsPerMinute = 250
const typingTimeout = (wordCount / typedWordsPerMinute) * 60000
sendAvatarOffset()
setTimeout(() => {
onTypingEnd()
}, typingTimeout)
}, [])
const onTypingEnd = () => {
setIsTyping(false)
setTimeout(() => {
sendAvatarOffset()
onTransitionEnd()
}, showAnimationDuration)
}
const sendAvatarOffset = () => {
if (!messageContainer.current) return
const containerDimensions = messageContainer.current.getBoundingClientRect()
updateLastAvatarOffset(containerDimensions.top + containerDimensions.height)
}
return (
<div className="flex flex-col" ref={messageContainer}>
<div className="flex mb-2 w-full lg:w-11/12 items-center">
<div className={'flex relative z-10 items-start typebot-host-bubble'}>
<div
className="flex items-center absolute px-4 py-2 rounded-lg bubble-typing z-10 "
style={{
width: isTyping ? '4rem' : '100%',
height: isTyping ? '2rem' : '100%',
}}
>
{isTyping ? <TypingContent /> : <></>}
</div>
{step.type === StepType.TEXT && (
<p
style={{
textOverflow: 'ellipsis',
}}
className={
'overflow-hidden content-opacity z-50 mx-4 my-2 whitespace-pre-wrap slate-html-container ' +
(isTyping ? 'opacity-0 h-6' : 'opacity-100 h-full')
}
dangerouslySetInnerHTML={{
__html: step.content.html,
}}
/>
)}
</div>
</div>
</div>
)
}

View File

@ -0,0 +1,9 @@
import React from 'react'
export const TypingContent = (): JSX.Element => (
<div className="flex items-center">
<div className="w-2 h-2 mr-1 rounded-full bubble1" />
<div className="w-2 h-2 mr-1 rounded-full bubble2" />
<div className="w-2 h-2 rounded-full bubble3" />
</div>
)