React Router学习报告
React Router学习报告
放上视频链接:[b站转载视频][a] youtube 课程文件github
准备知识
引入代码
1
2
3
4import {
createBrowserRouter,
RouterProvider,
} from "react-router-dom";基础结构,这里可以看到我们使用
<Main />
包裹了里面的内容,这里的Main组件包括了一些基础性内容,比如页面头部和底部。包裹起来进行路由跳转时,里面的组件也会拥有这些内容。1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21const router = createBrowserRouter([
{
path: "/",
element: <Main />,
loader: mainLoader,
errorElement: <Error />,
children: [
{
index: true,
element: <Dashboard />,
loader: dashboardLoader,
errorElement: <Error />
},
{
path: "logout",
action: logoutAction
}
]
},
])根据上面的例子的元素实例,和数据函数,请千万千万记住,在浏览器本地存储的时候密钥为key,值为value(字符串,加上双引号,我在这里debug快一个小时。。)如果数据加载异常不会有任何错误提示,路由会跳转到
<Error />
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20// loader
export function mainLoader(){
const userName = fetchData("userName");
return {userName}
}
const Main = () => {
const {userName} = useLoaderData()
return (
<div className='layout'>
<Nav userName={userName} />
<Outlet />
<img src={wave} alt="" />
</div>
)
}
export default MainfetchData函数
1
2
3
4
5
6
7
8
9// Loacl Storage
export const fetchData = (key) => {
return JSON.parse(localStorage.getItem(key));
};
//delete item
export const deleteItem = ({key}) => {
return localStorage.removeItem(key)
}
小知识
PS : 内容太多了,只能补充一些个人认为比较有用的知识了
使用lebel的htmlFor属性和input中的id属性对应,之后可以用于获取数据
1
2
3
4
5
6<label htmlFor="newExpense">Expense Name</label>
<input
type="text"
name="newExpense"
id="newExpense"
/>使用input
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20<input type="hidden" name="_action" value="deleteExpense" />
<input type="hidden" name="expenseId" value={expense.id} />
// 把input隐藏,将名称改为_action,之后通过一下代码获取分步处理
export async function dashboardAction({request}){
const data = await request.formData();
const {_action, ...values} = Object.fromEntries(data);
// 下面使用判断语句判断_action,然后try-catch,下面给出一个例子
if(_action === "deleteExpense"){
try{
deleteItem({
key: "expenses",
id: values.expenseId
})
return toast.success("Expense deleted!")
} catch(e){
throw new Error("There was a problem deleting your expense.")
}
}
// 请万分注意,我debug了快一个小时,因为id传递的参数写错了,必须和name相对应,之前不小心写成expenses直接找半天
}使用fetcher
1
2
3
4
5
6
7const fetcher = useFetcher();
// 使用fetcher
<fetcher.Form method="post" className="grid-sm" ref={formRef}>
</fetcher.Form>
// 把表单改为上面代码
// 可以通过这个检查状态idle loading submitting
const isSubmitting = fetcher.state === "submitting"使用Ref
1
2
3
4
5
6
7
8
9
10
11
12// 使用Ref来检测
const formRef = useRef();
const focusRef = useRef();
useEffect(() => {
if(!isSubmitting){
// clear form
formRef.current.reset()
// reset focus
focusRef.current.focus()
}
},[isSubmitting])
// 通过这个代码对提交的表单进行内容清空和重新focus,focusRef放到需要的input中
脑抽小bug
map使用
1
2
3
4{budgets.map((budget) => (
<BudgetItem key={budget.id} budget={budget} />
))}
// returning a valid JSX element inside map(),如果使用{}需要返回jsx元素,向上面这样写需要使用()
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 Change The World!