This example shows how to detect the intersecting faces using collision detection.
31#include <easy3d/renderer/drawable_triangles.h>
32#include <easy3d/renderer/manipulator.h>
33#include <easy3d/renderer/manipulated_frame.h>
34#include <easy3d/renderer/renderer.h>
35#include <easy3d/util/resource.h>
36#include <easy3d/algo/collider.h>
43TutorialCollisionDetection::TutorialCollisionDetection(
const std::string &title)
45 , model0_color_(0.8f, 1.0f, 0.8f)
46 , model1_color_(0.8f, 0.8f, 1.0f)
48 auto m0 = add_model(resource::directory() +
"/data/bunny.ply");
49 auto m1 = add_model(resource::directory() +
"/data/mannequin.ply");
57 mesh0->add_face_property<
vec3>(
"face_color", model0_color_);
61 mesh1->add_face_property<
vec3>(
"face_color", model1_color_);
64 collider_ =
new Collider(mesh0, mesh1);
68 timer_.set_interval(50, [
this]()->
void {
69 static std::mutex mutex;
70 std::lock_guard<std::mutex> guard(mutex);
71 static float angle = 0.0f;
73 auto T = mat4::rotation(
vec3(0, 0, 1), angle) * models_[0]->manipulator()->frame()->matrix();
74 models_[0]->manipulator()->frame()->setFromMatrix(T);
79 LOG(WARNING) <<
"not all the two meshes have been loaded";
82 "--------------------- Collision Viewer usage ----------------------\n"
83 "On start, you will see an animation with highlighted intersecting \n"
84 "faces. Press 'space' to pause/resume the animation. \n"
85 "When the animation is paused, you can manipulate the bunny model \n"
86 "(using your mouse) to perform real-time collection detection: \n"
87 " - Alt + left button: rotate bunny model \n"
88 " - Alt + right button: translate bunny model \n"
89 "------------------------------------------------------------------ \n";
91 hint_ =
"Press 'space' to pause/resume animation\n"
93 " - Alt + left button: rotate bunny model\n"
94 " - Alt + right button: translate bunny model";
98TutorialCollisionDetection::~TutorialCollisionDetection() {
104bool TutorialCollisionDetection::mouse_drag_event(
int x,
int y,
int dx,
int dy,
int button,
int modifiers) {
105 if (collider_ && models().size() == 2 && modifiers == MODIF_ALT && timer_.is_paused()) {
106 auto manipulator = models_[0]->manipulator();
107 if (button == BUTTON_LEFT)
108 manipulator->frame()->action_rotate(x, y, dx, dy, camera(), ManipulatedFrame::NONE);
109 else if (button == BUTTON_RIGHT)
110 manipulator->frame()->action_translate(x, y, dx, dy, camera(), ManipulatedFrame::NONE);
118 return Viewer::mouse_drag_event(x, y, dx, dy, button, modifiers);
122bool TutorialCollisionDetection::key_press_event(
int key,
int modifiers) {
123 if (key == KEY_SPACE) {
124 if (timer_.is_paused())
131 return Viewer::key_press_event(key, modifiers);
135void TutorialCollisionDetection::detect() {
136 const auto pairs = collider_->detect(models_[0]->manipulator()->matrix(), mat4::identity());
144 auto mesh0 =
dynamic_cast<SurfaceMesh *
>(models_[0].get());
145 auto mesh1 =
dynamic_cast<SurfaceMesh *
>(models_[1].get());
147 auto mesh1_colors = mesh1->get_face_property<
vec3>(
"face_color");
148 mesh0_colors.vector().assign(mesh0->n_faces(), model0_color_);
149 mesh1_colors.vector().assign(mesh1->n_faces(), model1_color_);
150 for (
const auto &pair : pairs) {
151 mesh0_colors[pair.first] =
vec3(1.0f, 0.0f, 0.0f);
152 mesh1_colors[pair.second] =
vec3(1.0f, 0.0f, 0.0f);
154 models_[0]->renderer()->update();
155 models_[1]->renderer()->update();
void set_manipulator(std::shared_ptr< Manipulator > manip)
Attaches a manipulator to this model.
Definition model.h:103
@ COLOR_PROPERTY
Using a color property.
Definition state.h:59
@ FACE
Property defined on faces.
Definition state.h:70
A halfedge data structure for polygonal meshes of 2-manifold.
Definition surface_mesh.h:51
FaceProperty< T > get_face_property(const std::string &name) const
Get the face property with name name of type T.
Definition surface_mesh.h:1811