Move actors and retrieve their world coordinates

Hello !

This discussion is related to:

I would like to:

  • move (translate) actors with slider
  • retrieve their position in world coordinate once moved

Is it possible ? I feel I don’t understand enough VTK and do something wrong, but can’t find what is the right way of doing it.

For now I tried, from this example:

  • set the position of the cone actor (with setPosition)
  • retrieve the world coordinates of the actor Center with getCenter

getCenter works only after a rendering took place it seems, so it is not updated unless I interact with the TrackballCamera.

I am looking also at this example

which seem to do the transformations in a more canonical way,
but still not able to get the actor world coordinates.

Thank you in advance !

I think this codepen may accomplish what you were trying to do: https://codepen.io/DrewLazzeriKitware/pen/OJjXxEj

There are a lot of concepts in VTK, but they are well organized! I really recommend getting comfortable with the main ideas by reading at least the summary chapters within the manuals, which you can find for free here: VTK Textbook and User's Guide now available for download - Kitware Blog

Thank you for the quick answer and the explanations !

Good advice for the book yes !

Regarding the codepen you provided, I think we have the same: the getCenter() is not updated if we log it.

getPosition() seems really the way to go, but on our real life case, it does not seem to be in ‘world coordinates’, that why I tried getCenter().

I try to dig a bit more about why on this example getPosition() and getCenter() (when interactor updates the view) are the same, and not on our case (a bit more complicated, with multiple actors).

The position is just an offset based on the dataset provided. You can call getBounds() on the dataset that you are rendering.

Thanks Sebastien !

That’s certainly another point where I am a bit lost because I have to gain more knowledge of VTK concepts: getBounds() should be called on the mapper or the source ?

Anyway, in the codepen provided by Drew, if I add those two lines to the slider callback:

console.log("Center!", actor.getCenter());
console.log("Bounds!", mapper.getBounds());

we can see well that neither the actor.getCenter() and mapper.getBounds() are updated when we change the slider position.

When we interact with the cone, actor.getCenter() is updated, but not mapper.getBounds().

actor.getBounds is in world coordinates and probably what you want

actor.getCenter is in world coordinates

Position is in world coordinates

Thank you Ken !

actor.getBounds() seems to do what I want, you are right, it is in our case in world coordinate,
and is updated as soon as actor.setPosition(x, y, z) is called.

I still don’t get what does actor.getCenter(), I will look into the source code.

Also, I have also to look why, in our code, actor.getPosition() gives something really different than the world positions.

Anyway I think we can proceed and this case is solved, thank you all !

Think of your data as already having some bounds (from the points in the file/source etc)

Then setPosition can be thought of as it if were setting a translation. What it does is set a translation that will be applied to the original data when rendered. Using a 1d example, if your original data has bounds of 10 to 20 and you did set position of 5 the new bounds would be 15,25 Hope that helps.

Thank you Ken, it helps a lot ! Now I think I really understood why in our case getPosition() (the translation) gives a different result than getBounds() (the world position), even if both are in world coordinates.

Hi again,

In the example from Drew:

and in our code, it happens that adding a call to getBounds() before getCenter() makes getCenter() to be updated (without having to interact with the view).

So let’s say in the slider callback I do:

console.log("Position!", actor.getPosition());
console.log("Bounds", actor.getBounds());
console.log("Center!", actor.getCenter());

getCenter() is updated correctly

It is like getBounds() does something more that getCenter()

You can see what getBounds() does (more than getCenter()) here: vtk-js/index.js at 3b816b9d6cff5846be0e7a7dda2dabf7721b947c · Kitware/vtk-js · GitHub

The comparison isn’t easy because getCenter is inherited (I think from here: vtk-js/index.js at df1258f781e520206d6cd830a0e64c27d7dfc61d · Kitware/vtk-js · GitHub) but you can see the function is much simpler and based on existing bounds.

Chapter 4 in the Vtk User’s Guide is a short overview of how these classes relate: https://vtk.org/wp-content/uploads/2021/08/VTKUsersGuide.pdf

You are right Drew, and the comments here are pretty clear !

    // Check if we have cached values for these bounds - we cache the
    // values returned by model.mapper.getBounds() and we store the time
    // of caching. If the values returned this time are different, or
    // the modified time of this class is newer than the cached time,
    // then we need to rebuild.

Thank you !