我认为这是一个足够简单的问题。我正在尝试在react中创建一个材质ui网格,并能够向其中添加行。我尝试了几种不同的模式,但都不起作用。我正在粘贴下面的示例,您可以在这里找到代码。
import React from "react";
import "./styles.css";
import { observer, useObservable } from "mobx-react-lite";
import MaterialTable from "material-table";
import Button from "@material-ui/core/Button";
const columns = [
{ title: "First Name", field: "name" },
{ title: "Last Name", field: "surname" },
{ title: "Year of Birth", field: "birthYear", type: "numeric" },
{
title: "City of Birth",
field: "birthCity",
lookup: {
34: "Haughton",
63: "San Diego",
88: "Henryetta"
}
}
];
const initialData = [
{ name: "Dak", surname: "Prescott", birthYear: 1993, birthCity: 34 }
];
const addData = [
{ name: "Troy", surname: "Aikman", birthYear: 1966, birthCity: 88 },
{ name: "Tony", surname: "Romo", birthYear: 1980, birthCity: 63 }
];
const App = observer(() => {
const store = useObservable({
data: initialData,
index: 0,
addRow() {
if (store.index < store.data.length) {
store.data.push(addData[store.index++]);
}
}
});
return (
<div className="App">
<MaterialTable
columns={columns}
data={store.data}
title="Sample Material Table"
/>
<Button onClick={() => store.addRow}>Add Row</Button>
</div>
);
});
export default App;
这只是一次尝试。我在单独的文件中创建了真正的Mobx存储,每个可观察的属性我都用@observable注释,但在这一点上,我绝对接受任何有效的东西。我已经让Mobx存储使用原生值(字符串和数字(,但不使用对象数组。我希望我只是遗漏了一些细微的差别。
您对修改存储的约定是正确的-通常,最好创建一个新的数组或对象,并在中合并新数据时将旧数据扩展到新数组或对象中。
我认为在您的情况下,您只是在onClick
处理程序中有一个拼写错误。您没有在Button元素中调用它——您正在运行一个箭头函数,但在内部您没有调用addRow
方法!我已经为您重写了它,还切换到了useLocalStore
钩子,因为这是目前推荐使用的钩子。
这也是回顾React中从onClick
属性调用函数的语法的好机会。
onClick={handleClick}
//传递对函数的引用,React会在元素被点击时自动调用该函数。您不需要手动调用它。换句话说,把父母放在这里是错误的。
onClick={() => handleClick}
//创建一个内联箭头函数,React会自动运行这个函数,就像上面一样。它将像执行正常函数一样执行每一行。它将到达标识符handleClick
,不再执行任何操作,因为在您创建的新箭头函数中没有调用handleClick。
onClick={() => handleClick()}
//与上面相同,因为您正在创建一个内联箭头函数。React会像上面一样运行这个箭头函数。它将执行每一行,然后调用你的函数,因为你用括号调用了它。
希望这能有所帮助!
顺便说一句,你需要验证从中获取新行的数据源是否能够接受你传递的索引。现在,如果你点击按钮两次以上,你会得到一个索引越界错误。但我假设你已经处理好了这一部分,所以我没有更改你代码的这一部分。
import React from "react";
import "./styles.css";
import { useObserver } from "mobx-react-lite";
import MaterialTable from "material-table";
import Button from "@material-ui/core/Button";
import { useLocalStore } from "mobx-react";
const columns = [
{ title: "First Name", field: "name" },
{ title: "Last Name", field: "surname" },
{ title: "Year of Birth", field: "birthYear", type: "numeric" },
{
title: "City of Birth",
field: "birthCity",
lookup: {
34: "Haughton",
63: "San Diego",
88: "Henryetta"
}
}
];
const initialData = [
{ name: "Dak", surname: "Prescott", birthYear: 1993, birthCity: 34 }
];
const addData = [
{ name: "Troy", surname: "Aikman", birthYear: 1966, birthCity: 88 },
{ name: "Tony", surname: "Romo", birthYear: 1980, birthCity: 63 }
];
const App = () => {
const store = useLocalStore(() => ({
data: initialData,
index: 0,
addRow() {
if (this.index < this.data.length) {
this.data = [...this.data, addData[this.index++]];
}
}
}));
return useObserver(() => (
<div className="App">
<MaterialTable
columns={columns}
data={store.data}
title="Sample Material Table"
/>
<Button onClick={store.addRow}>Add Row</Button>
</div>
));
};
export default App;
好的,我查看了其他带有material table标签的帖子,找到了问题的关键。我没有将一个元素推送到我的数据数组中,而是将数组设置为一个附加了新元素的全新数组。
store.data = [...store.data, addData[store.index++]];
事实证明,我上面的例子即使进行了更改也不起作用,但更改数组修饰符以返回新数组是解决方案的关键。