I am trying to use Viewport.TransformUnderMouse (in 2D environment).
When it finds TCastleScene object (just containing image) it returns the object and works fine.
But when the found object is of any other class for example TCastleImageTransform or TCastlePlane then the returned object’s Name parameter returns empty string and changing its parameters gives no effect.
Are there any extra steps needed to access TCastleImageTransform object returned from Viewport.TransformUnderMouse? I am using Lazarus and FPC 3.2.2 on Windows 10.
Background what was wrong: the TCastleImageTransform and TCastlePlane actually create an internal TCastleScene instance, and place it as “hidden” child of themselves. It is “hidden” just by setting the flag csTransient is ComponentStyle – so it’s hidden in inspector/editor, but otherwise all the code processes it is a regular child. And in this case, TransformUnderMouse was returning you this internal scene instance – it was indeed unnamed, and trying to modify it could have all sorts of weird effects (as parents like TCastleImageTransform and TCastlePlane treat it as internal to them).
I reproduced the problem in 3D, tweaking examples/viewport_and_scenes/detect_scene_hit. Screenshots after fixing attached
@michalis Is there any cge documentation how to use TransformUnderMouse?
Up until now I use a TCastleScene sprite image that is ‘locked’ to the mouse coordinates to collide with other objects.
And how can I hide the standard mouse cursor?
This my cge design tree:
Hiding the mouse cursor in Viewport (Viewport.Cursor:=mcNone) or ImageTransform does not hide the mouse, only when I set it in design property of Group1 but I want to turn it on and off while running the game code but then Group1.cursor := mcNone; is not recognised?
See API docs – Castle Game Engine: CastleViewport: Class TCastleViewport and the example I mentioned above, examples/viewport_and_scenes/detect_scene_hit. There isn’t that much to document, I hope the name is mostly self-explanatory It intuitively returns the current TCastleTransform under the mouse (or last touch position, on mobile).
I wanted to ask to create new topics for new questions But this happens to be related
Over TCastleViewport, it’s a bit special. Setting TCastleViewport.Cursor is currently just ignored and instead the TCastleViewport.Cursor is actually automatically overridden each frame following this trivial algorithm:
T := TransformUnderMouse;
if T <> nil then
Cursor := T.Cursor
Cursor := mcDefault;
So we use TCastleTransform.Cursor from the TransformUnderMouse. Or mcDefault if TransformUnderMouse is nil.
I don’t like much the AD 2 part – it is admittedly unexpected, makes the explanation more complicated than it should be. Maybe in the future we will just deprecate TCastleTransform.Cursor and let your code control TCastleViewport.Cursor explicitly.
Ah, that’s a trap I hope to remove at some point. The Container property of TUIState is set afterStart method has finished working (because only then the TUIState is UI child of container).
Long story short: if you write code inside Start method, use StartContainer instead of Container. So
StartContainer.OverrideCursor := ...
And yes, I hope to remove this “trap” at some point. Unfortunately the decision “how” is not easy – while it’s not intuitive that Container is not initialized here, but it is consistent with how UI children are initialized.
If I alternate try StartContainer.OverrideCursor it is not recognised so I guess this is okay because you replaced it with Container.OverrideCursor?
I also tried Container.OverrideCursor in other procedures than Start but with the same error.
Are you sure it is in latest CGE?