bool Selector::ProcessNaviMesh(Node *node, AI::NaviMesh *mesh) { if (mesh) { auto line = m_local_transform.top().Inversed() * m_view_ray; std::vector<Math::vec3> points; std::vector<size_t> faces; Math::Relation res = Math::CrossLineTriangles(line, mesh->GetPoints(), mesh->GetFaces(), points, faces); if (res == Math::Relation::INTERSECT) { // return points to the worlds coordinate system for (auto& p : points) { p = m_local_transform.top() * p; } Selection selection; selection.SetPoints(points); selection.SetFaces(faces); selection.SetObject(node); m_selections.push_back(selection); } } ProcessChildren(node); return true; }
bool Selector::ProcessTerrainMesh(Node *node, Virtual::TerrainMesh *terrain) { if (terrain) { Virtual::StaticGeometry* geom = terrain->GetGeometry(); if (geom) { Math::Line3D line = m_local_transform.top().Inversed() * m_view_ray; std::vector<Math::vec3> points; std::vector<size_t> faces; Math::Relation r = Math::CrossLineTriangles(line, geom->GetCpuCache().GetVertices(), geom->GetCpuCache().GetFaces(), points, faces); if (r == Math::Relation::INTERSECT) { Selection selection; // return points to the worlds coordinate system for (auto& p : points) { p = m_local_transform.top() * p; } selection.SetPoints(points); selection.SetFaces(faces); selection.SetObject(node); m_selections.push_back(selection); } } } ProcessChildren(node); return true; }
bool Selector::ProcessStaticGeometry(Node *node, Virtual::StaticGeometry *geom) { if (geom) { if (geom->GetCpuCache().IsOnCpu()) { bool has_bsphere = false; bool has_bbox = false; Math::Line3D line = m_local_transform.top().Inversed() * m_view_ray; if (m_check_bounding_sphere) { const Math::BoundingSphere& sphere = geom->GetBoundingSphere(); Math::vec3 p1, p2; Math::Relation r = Math::CrossLineSphere(line, sphere, p1, p2); if (r == Math::Relation::INTERSECT_2) { std::vector<Math::vec3> p(2); p[0]= m_local_transform.top() * p1; p[1] = m_local_transform.top() * p2; Selection s; s.SetPoints(p); s.SetType(SelectionType::BoundingSphere); s.SetObject(node); m_selections.push_back(s); has_bsphere = true; } if (r == Math::Relation::INTERSECT_1) { std::vector<Math::vec3> p(1); p[0]= m_local_transform.top() * p1; Selection s; s.SetPoints(p); s.SetType(SelectionType::BoundingSphere); s.SetObject(node); m_selections.push_back(s); has_bsphere = true; } } if (m_check_bounding_box) { if (has_bsphere || !m_check_bounding_sphere) { const Math::BoundingBox& bbox = geom->GetBoundingBox(); Math::vec3 p; Math::Relation r = Math::CrossLineBoundingBox(line, bbox, p); if (r == Math::Relation::INTERSECT) { std::vector<Math::vec3> points(1); points[0] = m_local_transform.top() * p; Selection s; s.SetPoints(points); s.SetType(SelectionType::BoundingBox); s.SetObject(node); m_selections.push_back(s); has_bbox = true; } } } if (m_check_geometry) { if (has_bbox || !m_check_bounding_box) { std::vector<Math::vec3> points; std::vector<size_t> faces; Math::Relation r = Math::CrossLineTriangles(line, geom->GetCpuCache().GetVertices(), geom->GetCpuCache().GetFaces(), points, faces); if (r == Math::Relation::INTERSECT) { // return points to the worlds coordinate system for (auto& p : points) { p = m_local_transform.top() * p; } Selection selection; selection.SetPoints(points); selection.SetFaces(faces); selection.SetType(SelectionType::Geometry); selection.SetObject(node); m_selections.push_back(selection); } } } } } return ProcessChildren(node); }