Skip to content

Commit

Permalink
new grabber
Browse files Browse the repository at this point in the history
  • Loading branch information
SoftFever committed Oct 16, 2023
1 parent 81260f5 commit 265ba87
Show file tree
Hide file tree
Showing 28 changed files with 501 additions and 571 deletions.
1 change: 1 addition & 0 deletions src/libslic3r/Model.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -1325,6 +1325,7 @@ class ModelInstance final : public ObjectBase
void transform_polygon(Polygon* polygon) const;

const Transform3d& get_matrix(bool dont_translate = false, bool dont_rotate = false, bool dont_scale = false, bool dont_mirror = false) const { return m_transformation.get_matrix(dont_translate, dont_rotate, dont_scale, dont_mirror); }
Transform3d get_matrix_no_offset() const { return m_transformation.get_matrix_no_offset(); }

bool is_printable() const { return object->printable && printable && (print_volume_state == ModelInstancePVS_Inside); }
bool is_assemble_initialized() { return m_assemble_initialized; }
Expand Down
85 changes: 15 additions & 70 deletions src/slic3r/GUI/Gizmos/GLGizmoAdvancedCut.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -512,62 +512,6 @@ void GLGizmoAdvancedCut::on_render()
render_cut_line();
}

void GLGizmoAdvancedCut::on_render_for_picking()
{
GLGizmoRotate3D::on_render_for_picking();

glsafe(::glDisable(GL_DEPTH_TEST));

BoundingBoxf3 box = m_parent.get_selection().get_bounding_box();
#if ENABLE_FIXED_GRABBER
float mean_size = (float)(GLGizmoBase::Grabber::FixedGrabberSize);
#else
float mean_size = (float)((box.size().x() + box.size().y() + box.size().z()) / 3.0);
#endif

std::array<float, 4> color = picking_color_component(0);
m_move_grabber.color[0] = color[0];
m_move_grabber.color[1] = color[1];
m_move_grabber.color[2] = color[2];
m_move_grabber.color[3] = color[3];
m_move_grabber.render_for_picking(mean_size);

glsafe(::glEnable(GL_DEPTH_TEST));
auto inst_id = m_c->selection_info()->get_active_instance();
if (inst_id < 0)
return;

const ModelObject *mo = m_c->selection_info()->model_object();
const ModelInstance *mi = mo->instances[inst_id];
const Vec3d & instance_offset = mi->get_offset();
const double sla_shift = double(m_c->selection_info()->get_sla_shift());

const CutConnectors &connectors = mo->cut_connectors;
for (int i = 0; i < connectors.size(); ++i) {
CutConnector connector = connectors[i];
Vec3d pos = connector.pos + instance_offset + sla_shift * Vec3d::UnitZ();
float height = connector.height;

const Camera &camera = wxGetApp().plater()->get_camera();
if (connector.attribs.type == CutConnectorType::Dowel && connector.attribs.style == CutConnectorStyle::Prizm) {
pos -= height * m_cut_plane_normal;
height *= 2;
} else if (!is_looking_forward())
pos -= 0.05 * m_cut_plane_normal;

Transform3d translate_tf = Transform3d::Identity();
translate_tf.translate(pos);

Transform3d scale_tf = Transform3d::Identity();
scale_tf.scale(Vec3f(connector.radius, connector.radius, height).cast<double>());

const Transform3d view_model_matrix = translate_tf * m_rotate_matrix * scale_tf;


std::array<float, 4> color = picking_color_component(i+1);
render_connector_model(m_shapes[connectors[i].attribs], color, view_model_matrix, true);
}
}

void GLGizmoAdvancedCut::on_render_input_window(float x, float y, float bottom_limit)
{
Expand Down Expand Up @@ -926,23 +870,24 @@ void GLGizmoAdvancedCut::render_cut_plane_and_grabbers()
else
render_color = GrabberColor;

GLModel &cube = m_move_grabber.get_cube();
// BBS set to fixed size grabber
// float fullsize = 2 * (dragging ? get_dragging_half_size(size) : get_half_size(size));
float fullsize = 8.0f;
if (GLGizmoBase::INV_ZOOM > 0) {
fullsize = m_move_grabber.FixedGrabberSize * GLGizmoBase::INV_ZOOM;
}
// Orca todo
// GLModel &cube = m_move_grabber.get_cube();
// // BBS set to fixed size grabber
// // float fullsize = 2 * (dragging ? get_dragging_half_size(size) : get_half_size(size));
// float fullsize = 8.0f;
// if (GLGizmoBase::INV_ZOOM > 0) {
// fullsize = m_move_grabber.FixedGrabberSize * GLGizmoBase::INV_ZOOM;
// }

cube.set_color(render_color);
// cube.set_color(render_color);

glsafe(::glPushMatrix());
glsafe(::glTranslated(m_move_grabber.center.x(), m_move_grabber.center.y(), m_move_grabber.center.z()));
glsafe(::glMultMatrixd(m_rotate_matrix.data()));
// glsafe(::glPushMatrix());
// glsafe(::glTranslated(m_move_grabber.center.x(), m_move_grabber.center.y(), m_move_grabber.center.z()));
// glsafe(::glMultMatrixd(m_rotate_matrix.data()));

glsafe(::glScaled(fullsize, fullsize, fullsize));
cube.render();
glsafe(::glPopMatrix());
// glsafe(::glScaled(fullsize, fullsize, fullsize));
// cube.render();
// glsafe(::glPopMatrix());

// Should be placed at last, because GLGizmoRotate3D clears depth buffer
set_center(m_cut_plane_center);
Expand Down
1 change: 0 additions & 1 deletion src/slic3r/GUI/Gizmos/GLGizmoAdvancedCut.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -147,7 +147,6 @@ struct Rotate_data {
virtual void on_stop_dragging() override;
virtual void on_update(const UpdateData& data);
virtual void on_render();
virtual void on_render_for_picking();
virtual void on_render_input_window(float x, float y, float bottom_limit);

void show_tooltip_information(float x, float y);
Expand Down
205 changes: 105 additions & 100 deletions src/slic3r/GUI/Gizmos/GLGizmoBase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,6 @@ namespace GUI {

float GLGizmoBase::INV_ZOOM = 1.0f;


const float GLGizmoBase::Grabber::SizeFactor = 0.05f;
const float GLGizmoBase::Grabber::MinHalfSize = 4.0f;
const float GLGizmoBase::Grabber::DraggingScaleFactor = 1.25f;
const float GLGizmoBase::Grabber::FixedGrabberSize = 16.0f;
const float GLGizmoBase::Grabber::FixedRadiusSize = 80.0f;


std::array<float, 4> GLGizmoBase::DEFAULT_BASE_COLOR = { 0.625f, 0.625f, 0.625f, 1.0f };
std::array<float, 4> GLGizmoBase::DEFAULT_DRAG_COLOR = { 1.0f, 1.0f, 1.0f, 1.0f };
std::array<float, 4> GLGizmoBase::DEFAULT_HIGHLIGHT_COLOR = { 1.0f, 0.38f, 0.0f, 1.0f };
Expand Down Expand Up @@ -68,27 +60,20 @@ void GLGizmoBase::load_render_colors()
RenderColor::colors[RenderCol_Flatten_Plane] = IMColor(GLGizmoBase::FLATTEN_COLOR);
RenderColor::colors[RenderCol_Flatten_Plane_Hover] = IMColor(GLGizmoBase::FLATTEN_HOVER_COLOR);
}
const float GLGizmoBase::Grabber::SizeFactor = 0.05f;
const float GLGizmoBase::Grabber::MinHalfSize = 1.5f;
const float GLGizmoBase::Grabber::DraggingScaleFactor = 1.25f;

GLGizmoBase::Grabber::Grabber()
: center(Vec3d::Zero())
, angles(Vec3d::Zero())
, dragging(false)
, enabled(true)
{
color = GRABBER_NORMAL_COL;
hover_color = GRABBER_HOVER_COL;
}
PickingModel GLGizmoBase::Grabber::s_cube;
PickingModel GLGizmoBase::Grabber::s_cone;

void GLGizmoBase::Grabber::render(bool hover, float size)
GLGizmoBase::Grabber::~Grabber()
{
std::array<float, 4> render_color;
if (hover) {
render_color = hover_color;
}
else
render_color = color;
if (s_cube.model.is_initialized())
s_cube.model.reset();

render(size, render_color, false);
if (s_cone.model.is_initialized())
s_cone.model.reset();
}

float GLGizmoBase::Grabber::get_half_size(float size) const
Expand All @@ -100,6 +85,7 @@ float GLGizmoBase::Grabber::get_dragging_half_size(float size) const
{
return get_half_size(size) * DraggingScaleFactor;
}

void GLGizmoBase::Grabber::register_raycasters_for_picking(int id)
{
picking_id = id;
Expand All @@ -113,51 +99,102 @@ void GLGizmoBase::Grabber::unregister_raycasters_for_picking()
raycasters = { nullptr };
}

GLModel& GLGizmoBase::Grabber::get_cube()
void GLGizmoBase::Grabber::render(float size, const ColorRGBA& render_color)
{
if (! cube_initialized) {
// This cannot be done in constructor, OpenGL is not yet
// initialized at that point (on Linux at least).
indexed_triangle_set mesh = its_make_cube(1., 1., 1.);
its_translate(mesh, Vec3f(-0.5, -0.5, -0.5));
cube.init_from(mesh);
cube_initialized = true;
}
return cube;
}
GLShaderProgram* shader = wxGetApp().get_current_shader();
if (shader == nullptr)
return;

void GLGizmoBase::Grabber::render(float size, const std::array<float, 4>& render_color, bool picking)
{
if (! cube_initialized) {
if (!s_cube.model.is_initialized()) {
// This cannot be done in constructor, OpenGL is not yet
// initialized at that point (on Linux at least).
indexed_triangle_set mesh = its_make_cube(1., 1., 1.);
its_translate(mesh, Vec3f(-0.5, -0.5, -0.5));
cube.init_from(mesh);
cube_initialized = true;
indexed_triangle_set its = its_make_cube(1.0, 1.0, 1.0);
its_translate(its, -0.5f * Vec3f::Ones());
s_cube.model.init_from(its);
s_cube.mesh_raycaster = std::make_unique<MeshRaycaster>(std::make_shared<const TriangleMesh>(std::move(its)));
}

//BBS set to fixed size grabber
//float fullsize = 2 * (dragging ? get_dragging_half_size(size) : get_half_size(size));
float fullsize = 8.0f;
if (GLGizmoBase::INV_ZOOM > 0) {
fullsize = FixedGrabberSize * GLGizmoBase::INV_ZOOM;
if (!s_cone.model.is_initialized()) {
indexed_triangle_set its = its_make_cone(0.375, 1.5, double(PI) / 18.0);
s_cone.model.init_from(its);
s_cone.mesh_raycaster = std::make_unique<MeshRaycaster>(std::make_shared<const TriangleMesh>(std::move(its)));
}

const float half_size = dragging ? get_dragging_half_size(size) : get_half_size(size);

s_cube.model.set_color(render_color);
s_cone.model.set_color(render_color);

const Camera& camera = wxGetApp().plater()->get_camera();
shader->set_uniform("projection_matrix", camera.get_projection_matrix());
const Transform3d& view_matrix = camera.get_view_matrix();
const Matrix3d view_matrix_no_offset = view_matrix.matrix().block(0, 0, 3, 3);
std::vector<Transform3d> elements_matrices(GRABBER_ELEMENTS_MAX_COUNT, Transform3d::Identity());
elements_matrices[0] = matrix * Geometry::translation_transform(center) * Geometry::rotation_transform(angles) * Geometry::scale_transform(2.0 * half_size);
Transform3d view_model_matrix = view_matrix * elements_matrices[0];

shader->set_uniform("view_model_matrix", view_model_matrix);
Matrix3d view_normal_matrix = view_matrix_no_offset * elements_matrices[0].matrix().block(0, 0, 3, 3).inverse().transpose();
shader->set_uniform("view_normal_matrix", view_normal_matrix);
s_cube.model.render();

auto render_extension = [&view_matrix, &view_matrix_no_offset, shader](const Transform3d& matrix) {
const Transform3d view_model_matrix = view_matrix * matrix;
shader->set_uniform("view_model_matrix", view_model_matrix);
const Matrix3d view_normal_matrix = view_matrix_no_offset * matrix.matrix().block(0, 0, 3, 3).inverse().transpose();
shader->set_uniform("view_normal_matrix", view_normal_matrix);
s_cone.model.render();
};

if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::PosX)) != 0) {
elements_matrices[1] = elements_matrices[0] * Geometry::translation_transform(Vec3d::UnitX()) * Geometry::rotation_transform({ 0.0, 0.5 * double(PI), 0.0 });
render_extension(elements_matrices[1]);
}
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::NegX)) != 0) {
elements_matrices[2] = elements_matrices[0] * Geometry::translation_transform(-Vec3d::UnitX()) * Geometry::rotation_transform({ 0.0, -0.5 * double(PI), 0.0 });
render_extension(elements_matrices[2]);
}
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::PosY)) != 0) {
elements_matrices[3] = elements_matrices[0] * Geometry::translation_transform(Vec3d::UnitY()) * Geometry::rotation_transform({ -0.5 * double(PI), 0.0, 0.0 });
render_extension(elements_matrices[3]);
}
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::NegY)) != 0) {
elements_matrices[4] = elements_matrices[0] * Geometry::translation_transform(-Vec3d::UnitY()) * Geometry::rotation_transform({ 0.5 * double(PI), 0.0, 0.0 });
render_extension(elements_matrices[4]);
}
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::PosZ)) != 0) {
elements_matrices[5] = elements_matrices[0] * Geometry::translation_transform(Vec3d::UnitZ());
render_extension(elements_matrices[5]);
}
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::NegZ)) != 0) {
elements_matrices[6] = elements_matrices[0] * Geometry::translation_transform(-Vec3d::UnitZ()) * Geometry::rotation_transform({ double(PI), 0.0, 0.0 });
render_extension(elements_matrices[6]);
}

cube.set_color(render_color);

glsafe(::glPushMatrix());
glsafe(::glTranslated(center.x(), center.y(), center.z()));
glsafe(::glRotated(Geometry::rad2deg(angles.z()), 0.0, 0.0, 1.0));
glsafe(::glRotated(Geometry::rad2deg(angles.y()), 0.0, 1.0, 0.0));
glsafe(::glRotated(Geometry::rad2deg(angles.x()), 1.0, 0.0, 0.0));
glsafe(::glScaled(fullsize, fullsize, fullsize));
cube.render();
glsafe(::glPopMatrix());
if (raycasters[0] == nullptr) {
GLCanvas3D& canvas = *wxGetApp().plater()->canvas3D();
raycasters[0] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cube.mesh_raycaster, elements_matrices[0]);
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::PosX)) != 0)
raycasters[1] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cone.mesh_raycaster, elements_matrices[1]);
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::NegX)) != 0)
raycasters[2] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cone.mesh_raycaster, elements_matrices[2]);
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::PosY)) != 0)
raycasters[3] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cone.mesh_raycaster, elements_matrices[3]);
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::NegY)) != 0)
raycasters[4] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cone.mesh_raycaster, elements_matrices[4]);
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::PosZ)) != 0)
raycasters[5] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cone.mesh_raycaster, elements_matrices[5]);
if ((int(extensions) & int(GLGizmoBase::EGrabberExtension::NegZ)) != 0)
raycasters[6] = canvas.add_raycaster_for_picking(SceneRaycaster::EType::Gizmo, picking_id, *s_cone.mesh_raycaster, elements_matrices[6]);
}
else {
for (size_t i = 0; i < GRABBER_ELEMENTS_MAX_COUNT; ++i) {
if (raycasters[i] != nullptr)
raycasters[i]->set_transform(elements_matrices[i]);
}
}
}


GLGizmoBase::GLGizmoBase(GLCanvas3D& parent, const std::string& icon_filename, unsigned int sprite_id)
: m_parent(parent)
, m_group_id(-1)
Expand Down Expand Up @@ -290,65 +327,33 @@ void GLGizmoBase::GizmoImguiSetNextWIndowPos(float &x, float y, int flag, float
m_imgui->set_next_window_pos(x, y, flag, pivot_x, pivot_y);
}

std::array<float, 4> GLGizmoBase::picking_color_component(unsigned int id) const
{
static const float INV_255 = 1.0f / 255.0f;

id = BASE_ID - id;

if (m_group_id > -1)
id -= m_group_id;

// color components are encoded to match the calculation of volume_id made into GLCanvas3D::_picking_pass()
return std::array<float, 4> {
float((id >> 0) & 0xff) * INV_255, // red
float((id >> 8) & 0xff) * INV_255, // green
float((id >> 16) & 0xff) * INV_255, // blue
float(picking_checksum_alpha_channel(id & 0xff, (id >> 8) & 0xff, (id >> 16) & 0xff))* INV_255 // checksum for validating against unwanted alpha blending and multi sampling
};
}


void GLGizmoBase::render_grabbers(const BoundingBoxf3& box) const
{
#if ENABLE_FIXED_GRABBER
render_grabbers((float)(GLGizmoBase::Grabber::FixedGrabberSize));
#else
render_grabbers((float)((box.size().x() + box.size().y() + box.size().z()) / 3.0));
#endif
}

void GLGizmoBase::render_grabbers(float size) const
{
render_grabbers(0, m_grabbers.size() - 1, size, false);
}

void GLGizmoBase::render_grabbers(size_t first, size_t last, float size, bool force_hover) const
{
GLShaderProgram* shader = wxGetApp().get_shader("gouraud_light");
if (shader == nullptr)
return;
shader->start_using();
shader->set_uniform("emission_factor", 0.1f);
for (int i = 0; i < (int)m_grabbers.size(); ++i) {
glsafe(::glDisable(GL_CULL_FACE));
for (size_t i = first; i <= last; ++i) {
if (m_grabbers[i].enabled)
m_grabbers[i].render(m_hover_id == i, size);
m_grabbers[i].render(force_hover ? true : m_hover_id == (int)i, size);
}
glsafe(::glEnable(GL_CULL_FACE));
shader->stop_using();
}

void GLGizmoBase::render_grabbers_for_picking(const BoundingBoxf3& box) const
{
#if ENABLE_FIXED_GRABBER
float mean_size = (float)(GLGizmoBase::Grabber::FixedGrabberSize);
#else
float mean_size = (float)((box.size().x() + box.size().y() + box.size().z()) / 3.0);
#endif

for (unsigned int i = 0; i < (unsigned int)m_grabbers.size(); ++i) {
if (m_grabbers[i].enabled) {
std::array<float, 4> color = picking_color_component(i);
m_grabbers[i].color = color;
m_grabbers[i].render_for_picking(mean_size);
}
}
}

std::string GLGizmoBase::format(float value, unsigned int decimals) const
{
return Slic3r::string_printf("%.*f", decimals, value);
Expand Down
Loading

0 comments on commit 265ba87

Please sign in to comment.