javascript - React Native:如何从子组件中的父组件访问变量?
问题描述
我正在尝试将我的 newsocket 变量从我的 MessagesScreen.js 传递给我的 ChatScreen.js。
我已经在这一点上停留了一段时间,并希望得到任何可能的帮助。我想要实现的是只发出一个连接,我可以在两个屏幕上收听事件。
现在在messagesScreen 上打开了连接。我现在的问题是,如果用户 1 在所有消息屏幕上,而用户 2 在聊天中。用户 2 向用户 1 发送消息,用户 1 的屏幕不会自动更新消息发送到的对话的最后一条消息,我需要滚动刷新或从一个页面导航到另一个页面才能显示.
这是我的代码:
父 --> messagesScreen.js
function MessagesScreen({navigation}) {
const [posts, setPosts] = useState([]);
const { user } = useAuth();
const [socket, setSocket] = useState(null);
const loadposts = async () => {
const response = await messagesApi.getMessages();// here i am loading all the conversation this user has
setPosts(response.data)
};
useEffect(() => {
newsocket = sockets(user.id); // newsocket is what i am trying to pass to child component
setSocket(newsocket);
loadPosts()
newsocket.on("send_message", (msg) => {
console.log("messages:", msg);
})
}, []);
return (
<FlatList
data={posts}
keyExtractor={(post) => post.id.toString()}
renderItem={({ item,index }) => (
<MessagesList
title={item.Post.title}
subTitle={item.Messages[0].message}
onPress={() => navigation.navigate(
routes.CHAT,{message:item,index,newsocket:socket})}
/>
)}
/>
)
孩子--->chatScreen.js
function ChatScreen({route,navigation,socket}) {
const [messages, setMessages] = useState([]);
const { user } = useAuth();
const index = route.params.index;
const message = route.params.message;
const newsocket = route.params.newsocket;
const loadListings = async () => {
const response = await messagesApi.getConversation(message.id);// here i am loading the messages in that specific conversation
setMessages(response.data.Messages)
};
useEffect(() => {
loadListings()
newsocket.emit('subscribe', message.id);
newsocket.on("send_message", (msg) => {
console.log("this is the chat messages:", msg);
setMessages(messages => [msg, ...messages]);
});
}, []);
const onSend = (ConversationId,senderId,receiverId,message) => {
const to = (user.id===route.params.message.user1?
route.params.message.user2:route.params.message.user1)
socket.emit('message', { to: to, from: user.id, message,ConversationId});
messagesApi.sendMessage({ConversationId,senderId,receiverId,message});
};
return(
<FlatList
inverted
data={messages}
keyExtractor={(item,index)=>index.toString()}
extraData={messages} // add this
renderItem={({item,index})=>(
<MessageBubble
text={item.message}
mine={item.senderId !== user.id}
/>
)}
/>
)
socket.js
import io from 'socket.io-client';
const newsocket = (user) => {
let newsocket = io.connect("http://192.168.1.107:9000")
newsocket.on('connect', msg => {
console.log(`waiting for user: ${user} to join a conversation`)
});
newsocket.emit('waiting', user);
return newsocket;
}
export default newsocket;
解决方案
我会以不同的方式处理这个问题。
- 您可以在单独的模块中将套接字连接创建为共享服务,然后将其简单地导入所需的相关组件中。在此共享模块中,您处理连接/断开连接并返回现有连接或创建新连接以返回。
快速粗略:
// socket-server.ts
import io from 'socket.io-client';
let socket: SocketIOClient.Socket = null;
export const getSocketServer = (): Promise<SocketIOClient.Socket> => {
return new Promise<SocketIOClient.Socket>(resolve => {
if (socket) {
console.info(`returning existing socket: ${socket.id}`);
return resolve(socket);
}
socket = io('http://localhost:4000', {
autoConnect: false,
});
socket.on('connect_error', (err) => {
console.error(err);
})
socket.on('connect', () => {
console.info(`creating new socket: ${socket.id}`);
return resolve(socket);
});
socket.open();
})
}
// then in your relevant modules
// module-a.ts
import React, {useEffect, useState} from 'react';
import {getSocketServer} from './../components/socket-server';
const Component = () => {
useEffect(() => {
const connect = async () => {
const socket = await getSocketServer();
socket.on('hello', (message) => {
console.info('hello from module A', message);
});
}
connect();
}, []);
return (
<>
<h2>Module A</h2>
</>
)
}
export default Component;
- 您也许还可以查看创建上下文提供程序并根据需要与相关模块共享套接字。
Context 提供了一种通过组件树传递数据的方法,而无需在每个级别手动传递 props。
推荐阅读
- javascript - 数据表不能与 javascript settimeout 功能一起使用?
- angular - 使用 [disabled] 时绑定不能包含分配
- python - 在python中下载文件时出现问题
- amazon-web-services - 在 AWS 中设置 SSL 时需要帮助
- javascript - 如果内部对象相同,则javascript合并数组
- python - 从树数据中找到根节点
- swift - 使用 Alamofire "format=json&body=" 格式化 HTTP 请求
- c++ - 这个指针对字符串流有什么作用?
- r - 用列表中的一些值计算每一行
- angular - 捆绑时导出角材料 - 使用 manfredsteyer/ngx-build-plus