-
Notifications
You must be signed in to change notification settings - Fork 0
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add arrow to selected lanes #223
Changes from 1 commit
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
// Copyright 2018 Toyota Research Institute | ||
|
||
#include "arrow_mesh.hh" | ||
#include <ignition/common/MeshManager.hh> | ||
#include <ignition/math/Helpers.hh> | ||
#include <ignition/rendering/Material.hh> | ||
#include <ignition/rendering/Mesh.hh> | ||
#include <ignition/rendering/Scene.hh> | ||
|
||
namespace delphyne { | ||
namespace gui { | ||
|
||
ArrowMesh::ArrowMesh(ignition::rendering::ScenePtr& _scene, double _zOffset, double _scaleFactor) | ||
: zOffset(_zOffset), | ||
scaleFactor(_scaleFactor), | ||
distanceToMove(zOffset / 4.0), | ||
step(0.005), | ||
totalTicks(distanceToMove / step), | ||
currentTick(0), | ||
currentDirection(-1) { | ||
ignition::rendering::MaterialPtr material = _scene->CreateMaterial(); | ||
material->SetDiffuse(255.0, 0.0, 0.0, 1.0); | ||
material->SetAmbient(255.0, 0.0, 0.0, 1.0); | ||
this->arrow = _scene->CreateVisual(); | ||
this->arrow->AddGeometry(_scene->CreateCone()); | ||
this->arrow->SetMaterial(material); | ||
this->arrow->SetVisible(false); | ||
this->arrow->SetWorldPosition(0., 0., 0.); | ||
this->arrow->SetWorldRotation(0, IGN_PI, 0.); | ||
_scene->RootVisual()->AddChild(this->arrow); | ||
this->CreateCylinder(_scene); | ||
ignition::common::MeshManager* meshManager = ignition::common::MeshManager::Instance(); | ||
const ignition::common::Mesh* unitConeMesh = meshManager->MeshByName("unit_cone"); | ||
minArrowBoundingBox = unitConeMesh->Min(); | ||
} | ||
|
||
void ArrowMesh::SelectAt(double _distanceFromCamera, const ignition::math::Vector3d& _worldPosition) { | ||
const double scaleIncrement = 1.0 + scaleFactor * _distanceFromCamera; | ||
const double newMinArrowBBZAxis = scaleIncrement * minArrowBoundingBox.Z(); | ||
this->arrow->SetWorldScale(scaleIncrement, scaleIncrement, scaleIncrement); | ||
this->arrow->SetWorldPosition(_worldPosition.X(), _worldPosition.Y(), | ||
_worldPosition.Z() + std::abs(newMinArrowBBZAxis) + zOffset); | ||
this->cylinder->SetWorldPosition(_worldPosition.X(), _worldPosition.Y(), | ||
_worldPosition.Z() + std::abs(minCylinderBoundingBox.Z())); | ||
currentDirection = -1; | ||
currentTick = 0; | ||
} | ||
|
||
void ArrowMesh::SetVisibility(bool _visible) { | ||
this->arrow->SetVisible(_visible); | ||
this->cylinder->SetVisible(_visible); | ||
} | ||
|
||
void ArrowMesh::Update() { | ||
ignition::math::Vector3d worldPosition = this->arrow->WorldPosition(); | ||
this->arrow->SetWorldPosition(worldPosition.X(), worldPosition.Y(), worldPosition.Z() + currentDirection * step); | ||
++currentTick; | ||
if (currentTick == totalTicks) { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @BMarchi nit: last two lines could be collapsed into one. |
||
currentDirection = currentDirection * -1; | ||
currentTick = 0; | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @BMarchi haha you did it. Consider turning There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @BMarchi nit: can we call |
||
} | ||
|
||
void ArrowMesh::CreateCylinder(ignition::rendering::ScenePtr& _scene) { | ||
ignition::rendering::MaterialPtr material = _scene->CreateMaterial(); | ||
material->SetDiffuse(255.0, 0.0, 0.0, 1.0); | ||
material->SetAmbient(255.0, 0.0, 0.0, 1.0); | ||
this->cylinder = _scene->CreateVisual(); | ||
this->cylinder->AddGeometry(_scene->CreateCylinder()); | ||
this->cylinder->SetMaterial(material); | ||
this->cylinder->SetVisible(false); | ||
this->cylinder->SetWorldPosition(0., 0., 0.); | ||
// This size is enough for visualization. | ||
this->cylinder->SetWorldScale(0.5, 0.5, 0.2); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @BMarchi as I told you offline, this is likely to run into some issues when dealing with very small lanes. Unless we somehow bound its size by the lane's area, which is going to be tough. Maybe once we get an outline we don't need this one anymore? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The arrow is useful but I think that with the outliner, the cylinder isn't necessary |
||
_scene->RootVisual()->AddChild(this->cylinder); | ||
ignition::common::MeshManager* meshManager = ignition::common::MeshManager::Instance(); | ||
const ignition::common::Mesh* unitCylinderMesh = meshManager->MeshByName("unit_cylinder"); | ||
minCylinderBoundingBox = unitCylinderMesh->Min(); | ||
minCylinderBoundingBox.X() = minCylinderBoundingBox.X() * 0.5; | ||
minCylinderBoundingBox.Y() = minCylinderBoundingBox.Y() * 0.5; | ||
minCylinderBoundingBox.Z() = minCylinderBoundingBox.Z() * 0.2; | ||
} | ||
|
||
} // namespace gui | ||
} // namespace delphyne |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,71 @@ | ||
// Copyright 2018 Toyota Research Institute | ||
|
||
#ifndef DELPHYNE_GUI_ARROW_MESH_HH | ||
#define DELPHYNE_GUI_ARROW_MESH_HH | ||
|
||
#include <ignition/math/Vector3.hh> | ||
#include <ignition/rendering/Scene.hh> | ||
|
||
namespace delphyne { | ||
namespace gui { | ||
|
||
/// \brief Renders a cone which will act as a pointing arrow when the user clicks over a lane | ||
class ArrowMesh { | ||
public: | ||
/// \brief Creates a cone and adds it as a child to the RootVisual of the scene, which will move | ||
/// upwards and downwards for a fixed amount of ticks. | ||
/// \param[in] _scene Scene pointer to create the cone. | ||
/// \param[in] _zOffset Units above the pointed object that the cone tip should be. | ||
/// \param[in] _scaleFactor Factor to increase/decrease the scale of the arrow based on the distance from the camera | ||
/// to the clicked position. | ||
ArrowMesh(ignition::rendering::ScenePtr& _scene, double _zOffset = 2.0, double _scaleFactor = 0.025); | ||
/// \brief Destructor. | ||
~ArrowMesh() = default; | ||
|
||
/// \brief Moves the arrow to a given world position and resets the downwards movement. | ||
/// \param[in] _distanceFromCamera How far the camera is from the clicked point. | ||
/// \param[in] _worldPosition World position of the cursor ray cast click. | ||
void SelectAt(double _distanceFromCamera, const ignition::math::Vector3d& _worldPosition); | ||
|
||
/// \brief Toggles the visibility of the arrow. | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @BMarchi nit: add one extra blank line here. |
||
/// \param[in] _visible Boolean that determines if the arrow should be visible or not. | ||
void SetVisibility(bool _visible); | ||
|
||
/// \brief Updates the position of the arrow moving slightly the z axis. | ||
void Update(); | ||
|
||
private: | ||
/// \brief Creates a red cylinder that will be below the arrow to emphasize the click position. | ||
void CreateCylinder(ignition::rendering::ScenePtr& _scene); | ||
|
||
/// \brief Bounding box of the cone in construction time. | ||
ignition::math::Vector3d minArrowBoundingBox; | ||
|
||
/// \brief Bounding box of the cylinder in construction time | ||
ignition::math::Vector3d minCylinderBoundingBox; | ||
|
||
/// \brief Visual pointer of the created cone. | ||
ignition::rendering::VisualPtr arrow; | ||
|
||
/// \brief Small cylinder that will be below the arrow to emphasize the click position. | ||
ignition::rendering::VisualPtr cylinder; | ||
|
||
/// \brief Units that the tip of the cone should be from the clicked position. | ||
const double zOffset; | ||
/// \brief Factor to increase/decrease the size of the cone. | ||
const double scaleFactor; | ||
/// \brief Distance to move downwards/upwards. | ||
const double distanceToMove; | ||
/// \brief How much units should the arrow move downwards/upwards per tick. | ||
const double step; | ||
/// \brief How much ticks required to move the arrow from down to up or up to down. | ||
const int totalTicks; | ||
/// \brief How many ticks passed since it started moving. | ||
int currentTick; | ||
/// \brief Tells the arrow if it should move upwards (1) or downwards (-1). | ||
int currentDirection; | ||
}; | ||
} // namespace gui | ||
} // namespace delphyne | ||
|
||
#endif // DELPHYNE_GUI_ARROW_MESH_HH |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@BMarchi I see what you're doing here, but does it scale appropriately if you zoom in/out? Should the scaling code be separate and called upon zoom?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In practice it looks fine to me. I wanted to avoid user interaction with the arrow's scale directly
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, I'll take a look locally.