如何在 Rust SPECS 中读取组件并写入具有相同组件的新实体?
How can I read from a component and write to a new entity with that same component in Rust SPECS?
我有一个正在生成其他实体的实体。比如生成器有位置组件,我想让生成的实体和生成器有相同的位置。
在生成系统中,我似乎需要同时读取和写入一个组件,这听起来不太可能。唯一的选择似乎是 LazyUpdate
,但我想避免这种情况,因为它需要调用 world::maintain
,并且我想在同一框架内的另一个系统中使用生成的实体。
我的系统代码:
#[derive(Debug)]
struct Position {
x: f32, // meters
y: f32,
z: f32,
direction: f32,
}
impl Component for Position {
type Storage = VecStorage<Self>;
}
struct GenerateEntity;
impl<'a> System<'a> for GenerateEntity {
type SystemData = (
ReadStorage<'a, Generator>,
ReadStorage<'a, Position>,
Entities<'a>,
);
fn run(&mut self, (gen, pos, entities): Self::SystemData) {
for (pos, gen) in (&pos, &gen).join() {
let generated = entities.create();
// This gives an error because position can only be read
pos.insert(generated, pos.clone());
}
}
}
如何解决这个问题?
it would seem that I would need to both read and write a component, which doesn't sound possible
当然是:使用 WriteStorage
.
这个名字有点误导。 WriteStorage
不是 write-only 存储;它是可变存储,包括读取。
唯一的问题是,您可能无法在遍历位置存储时插入它。您需要存储要在循环期间进行的更改并在之后应用它们。
(正如评论所指出的那样,您应该在循环中重命名 pos
(指的是单个组件),这样它就不会遮蔽您认为的 pos
参数(指的是整个存储))
我有一个正在生成其他实体的实体。比如生成器有位置组件,我想让生成的实体和生成器有相同的位置。
在生成系统中,我似乎需要同时读取和写入一个组件,这听起来不太可能。唯一的选择似乎是 LazyUpdate
,但我想避免这种情况,因为它需要调用 world::maintain
,并且我想在同一框架内的另一个系统中使用生成的实体。
我的系统代码:
#[derive(Debug)]
struct Position {
x: f32, // meters
y: f32,
z: f32,
direction: f32,
}
impl Component for Position {
type Storage = VecStorage<Self>;
}
struct GenerateEntity;
impl<'a> System<'a> for GenerateEntity {
type SystemData = (
ReadStorage<'a, Generator>,
ReadStorage<'a, Position>,
Entities<'a>,
);
fn run(&mut self, (gen, pos, entities): Self::SystemData) {
for (pos, gen) in (&pos, &gen).join() {
let generated = entities.create();
// This gives an error because position can only be read
pos.insert(generated, pos.clone());
}
}
}
如何解决这个问题?
it would seem that I would need to both read and write a component, which doesn't sound possible
当然是:使用 WriteStorage
.
这个名字有点误导。 WriteStorage
不是 write-only 存储;它是可变存储,包括读取。
唯一的问题是,您可能无法在遍历位置存储时插入它。您需要存储要在循环期间进行的更改并在之后应用它们。
(正如评论所指出的那样,您应该在循环中重命名 pos
(指的是单个组件),这样它就不会遮蔽您认为的 pos
参数(指的是整个存储))