reactjs - 组件安装后未选择频道列表中的第一项
问题描述
我想要实现的是,在从 firebase 实时数据库中获取频道后,我想自动从频道列表中选择第一项。
问题描述:组件挂载后,我想从 firebase 实时数据库中获取所有通道数据。然后我想选择第一项作为当前频道。看起来更新内部状态on("child_added", cb)
无法正常工作。
这是我的 Channels 组件的完整代码:
import React, { useState, useEffect } from "react";
import { Icon, Menu, Modal, Form, Input, Button } from "semantic-ui-react";
import { useForm } from "react-hook-form";
import { useDispatch, useSelector } from "react-redux";
import firebase from "../../firebase";
import { setCurrentChannel } from "../../redux/channelSlice";
export default function Channels({ currentUser }) {
const [channels, setChannels] = useState([]);
const [loading, setLoading] = useState(false);
const [showModal, setShowModal] = useState(false);
const channelsRef = firebase.database().ref("channels");
const { currentChannel } = useSelector((state) => state.channel);
const dispatch = useDispatch();
const { register, handleSubmit, setValue, trigger } = useForm();
const openModal = () => setShowModal(true);
const closeModal = () => setShowModal(false);
// form submit handler
const onSubmit = async (data) => {
setLoading(true);
const key = channelsRef.push().key;
const newChannel = {
id: key,
name: data.channelName,
details: data.channelDetails,
createdby: {
name: currentUser.displayName,
avatar: currentUser.photoURL,
},
};
try {
await channelsRef.child(key).update(newChannel);
closeModal();
setLoading(false);
} catch (error) {
setLoading(false);
console.log(error);
}
};
// Input Change Handler
const onInputChange = async (e, { name, value }) => {
setValue(name, value);
await trigger(name);
};
// Channnel list listener
const addListeners = () => {
channelsRef.on("child_added", (snap) => {
setChannels((currentChannels) => [...currentChannels, snap.val()]);
});
};
// Channel change Handler
const changeChannel = (channel) => {
dispatch(setCurrentChannel(channel));
};
useEffect(() => {
register({ name: "channelName" }, { required: true });
register({ name: "channelDetails" }, { required: true });
}, [register]);
useEffect(() => {
addListeners();
if (channels?.length) {
dispatch(setCurrentChannel(channels[0]));
}
// eslint-disable-next-line
}, []);
return (
<>
<Menu.Menu style={{ paddingBottom: "2em" }}>
<Menu.Item>
<span>
<Icon name="exchange" /> CHANNELS
</span>{" "}
({channels?.length})
<Icon name="add" onClick={openModal} style={{ cursor: "pointer" }} />
</Menu.Item>
{/* Channels */}
{channels?.map((channel) => (
<Menu.Item
key={channel.id}
onClick={() => changeChannel(channel)}
name={channel.name}
style={{ opacity: 0.7 }}
active={channel.id === currentChannel?.id}
>
# {channel.name}
</Menu.Item>
))}
</Menu.Menu>
{/* Add Channel Modal */}
<Modal
basic
open={showModal}
onClose={closeModal}
closeOnDimmerClick={false}
>
<Modal.Header>Add a Channel</Modal.Header>
<Modal.Content>
<Form id="channel-add-form" onSubmit={handleSubmit(onSubmit)}>
<Form.Field>
<Input
fluid
label="Name of channel"
name="channelName"
onChange={onInputChange}
/>
</Form.Field>
<Form.Field>
<Input
ref={register}
fluid
label="About the channel"
name="channelDetails"
onChange={onInputChange}
/>
</Form.Field>
</Form>
</Modal.Content>
<Modal.Actions>
<Button
form="channel-add-form"
type="submit"
color="green"
loading={loading}
>
<Icon name="checkmark" /> Add
</Button>
<Button color="red" onClick={closeModal}>
<Icon name="cancel" /> Cancel
</Button>
</Modal.Actions>
</Modal>
</>
);
}
解决方案
推荐阅读
- oracle - 游标循环 - 来自两个表的 COUNT - PLSQL Oracle
- python-3.x - Django-Q 每 X 秒调度一次任务
- spring - 使用旧的 ant_path_matcher 将 Zuul 切换到 Spring Api Gateway
- ios - 有没有办法检测我的应用打开了哪些 URL?
- javascript - 在 TypeError 上出现错误:无法读取未定义的属性“推送”
- html - 我有两个文本,我希望它们在 css 中相互显示
- python - 通过 Python HTTP 类保存 cookie
- ruby-on-rails - 如何将散列附加到另一个散列,其中这些散列是键的值?
- flutter - 无法在初始化程序中访问实例成员“小部件”。尝试用不同的表达式替换对实例成员的引用
- python - 匹配模式的正则表达式