Closed EricCousineau-TRI closed 8 months ago
To be perfectly frank, it took me several reads to appreciate what is being communicated here. I've erased my first babbling incomprehension in favor of this next pass.
Here's my best guess:
Does that basically capture it? The rest of the text assumes that my inference is correct.
dynamic
frame -- that means it is not rigidly affixed to its parent frame.However, as I look at the code and re-read it, I grow progressively less sure of this response. So, I'd ask, can you provide a code snippet of what you'd want to see that API you'd like that has a corresponding effect?
Yup, that captures it (sorry for the ambiguity!).
It would be nice to do something like the following:
const optional<geometry::FrameId> frame_id =
plant_->GetFrameIdIfExists(info.parent_frame->index());
DRAKE_THROW_UNLESS(frame_id.has_value());
auto camera =
builder.template AddSystem<systems::sensors::dev::RgbdCamera>(
camera_name, frame_id.value(), info.properties, false);
(removing offset to encourage people to add their frames during construction, since they will most likely want to add a camera in the physical model anywho.)
It's a very small change, but feels cleaner for reasons 1-3 that you cited above.
For response (2), it's not clear how expensive this would be, especially if, instead of registering bodies, frames were the main way to communicate between MBP and SG. I would think it could increase it by a factor of 4x, but it's just a pose bundle, and it's using cached kinematics when updating the pose?
If the computation / communication is expensive and we wish to save on it, it seems like SG (with non-trivial work, admittedly) could take a little more information on frame relationships (purely if it's rigidly fixed or not - nothing else) to save data.
This makes sense and I guess I have two thoughts:
RgbdCamera
(probably renamed to RgbdSensor
by the time it comes out of dev
) could take a constructor where the pose is default Identity
. That alleviates part of the problem.Does that satisfy things?
Yup, that'd be excellent!
I'd still like to advocate that we strip out all offsets, and always force users to add frames to the SG / MBP, but that can always happen after this.
The primary reason I can't subscribe to that philosophy is that I have to hew to the idea that SceneGraph
has to serve more than MBP.
For brief computations, like computing Jacobians with lots of offsets, I can understand a component not wanting to add permanent frames for those things (esp. if orientation has no meaning).
However, for something that is permanently being added (a camera, with individual frames per image), it would be really nice to have that accessible from more than just the RgbdCamera
output port / properties, without having to be too creative, and without having to excessively propagate those offsets and keep semantic track of them.
It's definitely not a huge requirement, but I have an inkling that it would simplify a lot of code. IMO, our code in Anzu is getting simplified because we've started using frames more, rather than an awkwardly redundant association of body + offset sprinkled throughout distinct locations in code / configuration.
To ground the discussion, is there a concrete non-MBP component that will be actively using SG that cannot add a frame to its scene graph when adding a camera for each of the frames it cares about?
You currently have the option of specifying a frame (with an Identity pose that could be sugared away). The current API doesn't preclude this. However, you're taking it a step further than I like by requiring a frame. Obviously, any geometry source can register frames. That capability is there. But the fact that one must introduce a frame to SG and preclude a non-identity pose for the camera seems to swing too far in the other direction. Ironically, it seems because the workflow you want isn't optimized, you're seeking to preclude alternate workflows.
The only way I could subscribe to this is if I were to introduce frames that were neither geometry frames (implied by geometries) nor dynamic frames. But, at that point, it's just a pose anyways. So, I am as yet unpersuaded on the real value there.
From my perspective, the real value is (a) code simplicity / maintainability (fewer public overloads with offsets) and (b) promoting cleaner workflows (make sure what you're adding has meaningful semantics). But yeah, I wouldn't say it's necessary for this issue at this point.
This came up again as a pain point (in Anzu).
That being said, I don't believe I will be able to address it. Unassigning myself, passing to @SeanCurtis-TRI for disposition (closing if you think it's not worth addressing).
(To clarify, I'd be happy to relax the philosophy of "requiring only frames and stripping out offsets".)
BTW It seems this whole thing would be happily resolved with a constructor overload -- i.e., specify the parent frame and have X_PB be identity by implication.
You'd still be responsible through some other means to make sure the frame you're affixing the camera to exists and is updated appropriately. But the camera doesn't have to know anything about it.
And, if you have a "dynamic frame" that is actually rigidly affixed to another dynamic frame, such that the total number of poses is increased by that one frame...who cares? It's not like the number of camera frames is really going to dominate.
If you agree, I'll knock out a quick PR.
Possibly this is a duplicate of #15002. Or at least, they are related.
Two thoughts:
CameraConfig
has been introduced and mitigates this. The pose X_PB
of the camera sensor can specify arbitrary frames. That arbitrary frame gets handled in the depths of the camera config functions (technically,in sim_rgbd_sensor.cc
).Generally, we should be pushing people towards using the config function for adding a camera. If they do this, the problems encountered in the code snippets evaporate completely.
For those reasons, I'm closing this issue. If anyone disagrees, feel free to re-open with the rebuttal.
Thanks! Agreed this can be closed out as duplicate of Russ's issue. Agreed on "config for camera workflow". I still have reservations on a pure code workflow, but I think that is fully captured by Russ's issue.
At present, it seems like we only have a mapping from a plant's body to a
FrameId
; if we want to get an arbitrary frame's mapping to the scene graph, we have to do an awkwardly redundant offset dance: https://github.com/RobotLocomotion/drake/blob/53f44f47c4e399b7573bcbe23b028cf57082011b/examples/manipulation_station/manipulation_station.cc#L462-L472It would be nice if a user to explicitly say that they want SG to handle a frame, thus we don't have to do the dance; instead, we could do
plant.GetFrameIdIfItExists(frame)
. In the manip station case, the camera frames are not added to the plant, but in Anzu in other cases, we do have the camera frames added (and TBH, I very much like it that way).@SeanCurtis-TRI Would adding something like
MBP::RegisterSceneGraphFrame(const Frame&)
be the right way to do this? (Would it be horrible for performance?)