I'm creating a simulated chat experience where at obj4, the user has a button to click to initiate their session.
Everything works fine showing messages 1-4 but when messages.length === 4 and I check initiated === true, weird stuff starts happening: prev, which usually returns the messages in the correct order, now returns the messages in the reverse order. And calling .reverse() or setting prev to a new variable and then calling reverse() doesn't work either.
The whole order of messages breaks when I check if (initiated === true) but if I don't, everything renders in the order I expect.
Any idea what's happening here?
import { useState, useEffect } from "react"
const chattest = () => {
const [messages, setMessages] = useState([])
const [initiated, setInitiated] = useState(false)
const obj1 = {
type: 'text',
text: '1',
action: function() {}
}
const obj2 = {
type: 'text',
text: '2',
action: function() {}
}
const obj3 = {
type: 'text',
text: '3',
action: function() {}
}
const obj4 = {
type: 'button',
text: initiated ? 'Initiated!' : 'Initiate',
state: initiated,
action: function() {
console.log('setting initiated')
setInitiated(true)
}
}
const obj5 = {
type: 'text',
text: 'initiated set!',
action: function() {}
}
useEffect(() => {
switch(messages.length) {
case 0:
setMessages([obj1])
case 1:
setMessages((prev) => [...prev, obj2])
case 2:
setMessages((prev) => [...prev, obj3])
case 3:
setMessages((prev) => [...prev, obj4])
case 4:
if (initiated) { // behavior changes here if I use this line
setMessages((prev) => {
console.log('prev', prev)
console.log('prev reversed', prev.reverse()) // this doesnt work
return [...prev, obj5]
})
}
default:
break
}
}, [messages, initiated])
return (
<div className="flex flex-col-reverse border border-solid border-black-500 w-[50%] mx-auto h-screen text-black">
{
messages.reverse().map((message, index) => {
const { type, text, state, action } = message
return <div key={index}>
<ChatFactory type={type} state={state} _text={text} action={action} />
</div>
})
}
</div>
)
}
export default chattest
const ChatFactory = ({type,_text, state,action}) => {
return (
type === 'text'
? (
<p>{_text}</p>
)
: (
<button onClick={action}>
{ _text}
</button>
)
)
}
from setState(prev) returning previous state in reverse order than expected when referencing another useState var in a useEffect
No comments:
Post a Comment