React SetState 数组不更新
React SetState array not updating
我的 React 应用程序中有一个 Google 地图,允许用户注册(通过输入他们的名字)。然后它每 1 秒获取一次他们的位置,并将其发送给当前使用该应用程序的所有其他用户。
我正在尝试使用 google-map-react 在地图上绘制用户。这应该在每次添加用户或他们的位置发生变化时更新,并通过他们在地图上移动的标记来反映这一点。
控制台正确记录了 usersArray,但用户没有更新,我的 setState 设置错了吗?
const Map = ({ location, zoomLevel }) => {
const { name } = useParams();
const [messages, setMessages] = useState([]);
const ws = useRef();
let [latitude, setLatitude] = useState('');
let [longitude, setLongitude] = useState('');
const [isConnectionOpen, setConnectionOpen] = useState(false);
const [users, setUsers] = useState([]);
useEffect(() => {
ws.current = new WebSocket('ws://localhost:8081');
//new user has connected
ws.current.onopen = () => {
setConnectionOpen(true);
};
//sending message to other users
ws.current.onmessage = (ev) => {
const message = JSON.parse(ev.data);
//update users function
handleAddNewUser(message);
setMessages((_messages) => [..._messages, message]);
};
return () => {};
}, []);
//checks if a message has been received my a new user. If existing user - update location
function handleAddNewUser(message) {
let usersArray = [];
let newUser = true;
if (users.length == 0) {
usersArray.push(message);
} else {
for (let user of users) {
if (message.sender == user.sender) {
newUser = false;
user = message;
}
}
if (newUser == true) {
usersArray.push(message);
}
}
console.log(usersArray);
// update the state to the updatedUsers
setUsers(usersArray);
console.log(users);
}
//triggers the send function every 1 second
useEffect(() => {
const interval = setInterval(() => {
send();
}, 1000);
return () => clearInterval(interval);
}, []);
//sends the users location as a message to all the other users
const send = () => {
if (navigator.geolocation) {
navigator.geolocation.watchPosition(function (position) {
latitude = position.coords.latitude.toString();
longitude = position.coords.longitude.toString();
ws.current.send(JSON.stringify({ sender: name, latitude: latitude, longitude: longitude }));
setLatitude('');
setLongitude('');
});
}
};
return (
<div className='map'>
<div className='google-map'>
<GoogleMapReact
bootstrapURLKeys={{ key: 'keyID' }}
defaultCenter={location}
defaultZoom={zoomLevel}>
users.map(user => {
<MyGreatPlace lat={user.latitude}
lng={user.longitude} text=
{user.sender} />
})
</GoogleMapReact>
</div>
</div>
);
};
export default Map;
此外,在地图上绘制用户时,出现此错误:意外标记。您是指 {'>'} 还是 >?
您应该先检查用户是否存在。像这样:
如果(用户){
设置用户(用户数组)
}
尝试将 useEffect
中的用户与依赖项数组中的用户一起登录。
但是您的组件中有两个 useEffects
。你应该只有一个!
//triggers the send function every 1 second
useEffect(() => {
console.log(users)
const interval = setInterval(() => {
send();
}, 1000);
return () => clearInterval(interval);
}, [users]);
为了 map
渲染 users
你通常会这样做(例如):
<GoogleMapReact bootstrapURLKeys={{ key: 'keyID' }} defaultCenter={location} defaultZoom={zoomLevel}>
{users?.map((user: any) => {
return <MyGreatPlace lat={user.latitude} lng={user.longitude} text={user.sender} />
})
}
</GoogleMapReact>
我的 React 应用程序中有一个 Google 地图,允许用户注册(通过输入他们的名字)。然后它每 1 秒获取一次他们的位置,并将其发送给当前使用该应用程序的所有其他用户。
我正在尝试使用 google-map-react 在地图上绘制用户。这应该在每次添加用户或他们的位置发生变化时更新,并通过他们在地图上移动的标记来反映这一点。
控制台正确记录了 usersArray,但用户没有更新,我的 setState 设置错了吗?
const Map = ({ location, zoomLevel }) => {
const { name } = useParams();
const [messages, setMessages] = useState([]);
const ws = useRef();
let [latitude, setLatitude] = useState('');
let [longitude, setLongitude] = useState('');
const [isConnectionOpen, setConnectionOpen] = useState(false);
const [users, setUsers] = useState([]);
useEffect(() => {
ws.current = new WebSocket('ws://localhost:8081');
//new user has connected
ws.current.onopen = () => {
setConnectionOpen(true);
};
//sending message to other users
ws.current.onmessage = (ev) => {
const message = JSON.parse(ev.data);
//update users function
handleAddNewUser(message);
setMessages((_messages) => [..._messages, message]);
};
return () => {};
}, []);
//checks if a message has been received my a new user. If existing user - update location
function handleAddNewUser(message) {
let usersArray = [];
let newUser = true;
if (users.length == 0) {
usersArray.push(message);
} else {
for (let user of users) {
if (message.sender == user.sender) {
newUser = false;
user = message;
}
}
if (newUser == true) {
usersArray.push(message);
}
}
console.log(usersArray);
// update the state to the updatedUsers
setUsers(usersArray);
console.log(users);
}
//triggers the send function every 1 second
useEffect(() => {
const interval = setInterval(() => {
send();
}, 1000);
return () => clearInterval(interval);
}, []);
//sends the users location as a message to all the other users
const send = () => {
if (navigator.geolocation) {
navigator.geolocation.watchPosition(function (position) {
latitude = position.coords.latitude.toString();
longitude = position.coords.longitude.toString();
ws.current.send(JSON.stringify({ sender: name, latitude: latitude, longitude: longitude }));
setLatitude('');
setLongitude('');
});
}
};
return (
<div className='map'>
<div className='google-map'>
<GoogleMapReact
bootstrapURLKeys={{ key: 'keyID' }}
defaultCenter={location}
defaultZoom={zoomLevel}>
users.map(user => {
<MyGreatPlace lat={user.latitude}
lng={user.longitude} text=
{user.sender} />
})
</GoogleMapReact>
</div>
</div>
);
};
export default Map;
此外,在地图上绘制用户时,出现此错误:意外标记。您是指 {'>'} 还是 >?
您应该先检查用户是否存在。像这样:
如果(用户){ 设置用户(用户数组) }
尝试将 useEffect
中的用户与依赖项数组中的用户一起登录。
但是您的组件中有两个 useEffects
。你应该只有一个!
//triggers the send function every 1 second
useEffect(() => {
console.log(users)
const interval = setInterval(() => {
send();
}, 1000);
return () => clearInterval(interval);
}, [users]);
为了 map
渲染 users
你通常会这样做(例如):
<GoogleMapReact bootstrapURLKeys={{ key: 'keyID' }} defaultCenter={location} defaultZoom={zoomLevel}>
{users?.map((user: any) => {
return <MyGreatPlace lat={user.latitude} lng={user.longitude} text={user.sender} />
})
}
</GoogleMapReact>