Some changing in implementation of emulate_kill_focus according to new code architecture.
+ Cleaning of the code from unused parts
This commit is contained in:
parent
59a6318931
commit
c1bb34cc4d
@ -120,9 +120,6 @@ static void set_font_and_background_style(wxWindow* win, const wxFont& font)
|
|||||||
|
|
||||||
ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||||
OG_Settings(parent, true)
|
OG_Settings(parent, true)
|
||||||
#ifndef __APPLE__
|
|
||||||
, m_focused_option("")
|
|
||||||
#endif // __APPLE__
|
|
||||||
{
|
{
|
||||||
m_manifold_warning_bmp = ScalableBitmap(parent, "exclamation");
|
m_manifold_warning_bmp = ScalableBitmap(parent, "exclamation");
|
||||||
|
|
||||||
@ -415,292 +412,6 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
|||||||
m_og->sizer->Add(m_main_grid_sizer, 1, wxEXPAND | wxALL, border);
|
m_og->sizer->Add(m_main_grid_sizer, 1, wxEXPAND | wxALL, border);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
|
||||||
OG_Settings(parent, true)
|
|
||||||
#ifndef __APPLE__
|
|
||||||
, m_focused_option("")
|
|
||||||
#endif // __APPLE__
|
|
||||||
{
|
|
||||||
m_manifold_warning_bmp = ScalableBitmap(parent, "exclamation");
|
|
||||||
m_og->set_name(_(L("Object Manipulation")));
|
|
||||||
m_og->label_width = 12;//125;
|
|
||||||
m_og->set_grid_vgap(5);
|
|
||||||
|
|
||||||
m_og->m_on_change = std::bind(&ObjectManipulation::on_change, this, std::placeholders::_1, std::placeholders::_2);
|
|
||||||
m_og->m_fill_empty_value = std::bind(&ObjectManipulation::on_fill_empty_value, this, std::placeholders::_1);
|
|
||||||
|
|
||||||
m_og->m_set_focus = [this](const std::string& opt_key)
|
|
||||||
{
|
|
||||||
#ifndef __APPLE__
|
|
||||||
m_focused_option = opt_key;
|
|
||||||
#endif // __APPLE__
|
|
||||||
|
|
||||||
// needed to show the visual hints in 3D scene
|
|
||||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(opt_key, true);
|
|
||||||
};
|
|
||||||
|
|
||||||
ConfigOptionDef def;
|
|
||||||
|
|
||||||
Line line = Line{ "Name", "Object name" };
|
|
||||||
|
|
||||||
auto manifold_warning_icon = [this](wxWindow* parent) {
|
|
||||||
m_fix_throught_netfab_bitmap = new wxStaticBitmap(parent, wxID_ANY, wxNullBitmap);
|
|
||||||
|
|
||||||
if (is_windows10())
|
|
||||||
m_fix_throught_netfab_bitmap->Bind(wxEVT_CONTEXT_MENU, [this](wxCommandEvent &e)
|
|
||||||
{
|
|
||||||
// if object/sub-object has no errors
|
|
||||||
if (m_fix_throught_netfab_bitmap->GetBitmap().GetRefData() == wxNullBitmap.GetRefData())
|
|
||||||
return;
|
|
||||||
|
|
||||||
wxGetApp().obj_list()->fix_through_netfabb();
|
|
||||||
update_warning_icon_state(wxGetApp().obj_list()->get_mesh_errors_list());
|
|
||||||
});
|
|
||||||
|
|
||||||
return m_fix_throught_netfab_bitmap;
|
|
||||||
};
|
|
||||||
|
|
||||||
line.near_label_widget = manifold_warning_icon;
|
|
||||||
def.label = "";
|
|
||||||
def.gui_type = "legend";
|
|
||||||
def.tooltip = L("Object name");
|
|
||||||
#ifdef __APPLE__
|
|
||||||
def.width = 20;
|
|
||||||
#else
|
|
||||||
def.width = 22;
|
|
||||||
#endif
|
|
||||||
def.set_default_value(new ConfigOptionString{ " " });
|
|
||||||
line.append_option(Option(def, "object_name"));
|
|
||||||
m_og->append_line(line);
|
|
||||||
|
|
||||||
const int field_width = 5;
|
|
||||||
|
|
||||||
// Mirror button size:
|
|
||||||
const int mirror_btn_width = 3;
|
|
||||||
|
|
||||||
// Legend for object modification
|
|
||||||
line = Line{ "", "" };
|
|
||||||
def.label = "";
|
|
||||||
def.type = coString;
|
|
||||||
def.width = field_width - mirror_btn_width;
|
|
||||||
|
|
||||||
// Load bitmaps to be used for the mirroring buttons:
|
|
||||||
m_mirror_bitmap_on = ScalableBitmap(parent, "mirroring_on");
|
|
||||||
m_mirror_bitmap_off = ScalableBitmap(parent, "mirroring_off");
|
|
||||||
m_mirror_bitmap_hidden = ScalableBitmap(parent, "mirroring_transparent.png");
|
|
||||||
|
|
||||||
static const char axes[] = { 'X', 'Y', 'Z' };
|
|
||||||
for (size_t axis_idx = 0; axis_idx < sizeof(axes); axis_idx++) {
|
|
||||||
const char label = axes[axis_idx];
|
|
||||||
def.set_default_value(new ConfigOptionString{ std::string(" ") + label });
|
|
||||||
Option option(def, std::string() + label + "_axis_legend");
|
|
||||||
|
|
||||||
// We will add a button to toggle mirroring to each axis:
|
|
||||||
auto mirror_button = [this, mirror_btn_width, axis_idx, label](wxWindow* parent) {
|
|
||||||
wxSize btn_size(em_unit(parent) * mirror_btn_width, em_unit(parent) * mirror_btn_width);
|
|
||||||
auto btn = new ScalableButton(parent, wxID_ANY, "mirroring_off", wxEmptyString, btn_size, wxDefaultPosition, wxBU_EXACTFIT | wxNO_BORDER | wxTRANSPARENT_WINDOW);
|
|
||||||
btn->SetToolTip(wxString::Format(_(L("Toggle %c axis mirroring")), (int)label));
|
|
||||||
btn->SetBitmapDisabled_(m_mirror_bitmap_hidden);
|
|
||||||
|
|
||||||
m_mirror_buttons[axis_idx].first = btn;
|
|
||||||
m_mirror_buttons[axis_idx].second = mbShown;
|
|
||||||
auto sizer = new wxBoxSizer(wxHORIZONTAL);
|
|
||||||
sizer->Add(btn);
|
|
||||||
|
|
||||||
btn->Bind(wxEVT_BUTTON, [this, axis_idx](wxCommandEvent &e) {
|
|
||||||
Axis axis = (Axis)(axis_idx + X);
|
|
||||||
if (m_mirror_buttons[axis_idx].second == mbHidden)
|
|
||||||
return;
|
|
||||||
|
|
||||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
|
||||||
Selection& selection = canvas->get_selection();
|
|
||||||
|
|
||||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
|
||||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(*selection.get_volume_idxs().begin()));
|
|
||||||
volume->set_volume_mirror(axis, -volume->get_volume_mirror(axis));
|
|
||||||
}
|
|
||||||
else if (selection.is_single_full_instance()) {
|
|
||||||
for (unsigned int idx : selection.get_volume_idxs()){
|
|
||||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(idx));
|
|
||||||
volume->set_instance_mirror(axis, -volume->get_instance_mirror(axis));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
return;
|
|
||||||
|
|
||||||
// Update mirroring at the GLVolumes.
|
|
||||||
selection.synchronize_unselected_instances(Selection::SYNC_ROTATION_GENERAL);
|
|
||||||
selection.synchronize_unselected_volumes();
|
|
||||||
// Copy mirroring values from GLVolumes into Model (ModelInstance / ModelVolume), trigger background processing.
|
|
||||||
canvas->do_mirror(L("Set Mirror"));
|
|
||||||
UpdateAndShow(true);
|
|
||||||
});
|
|
||||||
|
|
||||||
return sizer;
|
|
||||||
};
|
|
||||||
|
|
||||||
option.side_widget = mirror_button;
|
|
||||||
line.append_option(option);
|
|
||||||
}
|
|
||||||
line.near_label_widget = [this](wxWindow* parent) {
|
|
||||||
wxBitmapComboBox *combo = create_word_local_combo(parent);
|
|
||||||
combo->Bind(wxEVT_COMBOBOX, ([this](wxCommandEvent &evt) { this->set_world_coordinates(evt.GetSelection() != 1); }), combo->GetId());
|
|
||||||
m_word_local_combo = combo;
|
|
||||||
return combo;
|
|
||||||
};
|
|
||||||
m_og->append_line(line);
|
|
||||||
|
|
||||||
auto add_og_to_object_settings = [this, field_width](const std::string& option_name, const std::string& sidetext)
|
|
||||||
{
|
|
||||||
Line line = { _(option_name), "" };
|
|
||||||
ConfigOptionDef def;
|
|
||||||
def.type = coFloat;
|
|
||||||
def.set_default_value(new ConfigOptionFloat(0.0));
|
|
||||||
def.width = field_width;
|
|
||||||
|
|
||||||
if (option_name == "Scale") {
|
|
||||||
// Add "uniform scaling" button in front of "Scale" option
|
|
||||||
line.near_label_widget = [this](wxWindow* parent) {
|
|
||||||
auto btn = new LockButton(parent, wxID_ANY);
|
|
||||||
btn->Bind(wxEVT_BUTTON, [btn, this](wxCommandEvent &event){
|
|
||||||
event.Skip();
|
|
||||||
wxTheApp->CallAfter([btn, this]() { set_uniform_scaling(btn->IsLocked()); });
|
|
||||||
});
|
|
||||||
m_lock_bnt = btn;
|
|
||||||
return btn;
|
|
||||||
};
|
|
||||||
// Add reset scale button
|
|
||||||
auto reset_scale_button = [this](wxWindow* parent) {
|
|
||||||
auto btn = new ScalableButton(parent, wxID_ANY, ScalableBitmap(parent, "undo"));
|
|
||||||
btn->SetToolTip(_(L("Reset scale")));
|
|
||||||
m_reset_scale_button = btn;
|
|
||||||
auto sizer = new wxBoxSizer(wxHORIZONTAL);
|
|
||||||
sizer->Add(btn, wxBU_EXACTFIT);
|
|
||||||
btn->Bind(wxEVT_BUTTON, [this](wxCommandEvent &e) {
|
|
||||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _(L("Reset scale")));
|
|
||||||
change_scale_value(0, 100.);
|
|
||||||
change_scale_value(1, 100.);
|
|
||||||
change_scale_value(2, 100.);
|
|
||||||
});
|
|
||||||
return sizer;
|
|
||||||
};
|
|
||||||
line.append_widget(reset_scale_button);
|
|
||||||
}
|
|
||||||
else if (option_name == "Rotation") {
|
|
||||||
// Add reset rotation button
|
|
||||||
auto reset_rotation_button = [this](wxWindow* parent) {
|
|
||||||
auto btn = new ScalableButton(parent, wxID_ANY, ScalableBitmap(parent, "undo"));
|
|
||||||
btn->SetToolTip(_(L("Reset rotation")));
|
|
||||||
m_reset_rotation_button = btn;
|
|
||||||
auto sizer = new wxBoxSizer(wxHORIZONTAL);
|
|
||||||
sizer->Add(btn, wxBU_EXACTFIT);
|
|
||||||
btn->Bind(wxEVT_BUTTON, [this](wxCommandEvent &e) {
|
|
||||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
|
||||||
Selection& selection = canvas->get_selection();
|
|
||||||
|
|
||||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
|
||||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(*selection.get_volume_idxs().begin()));
|
|
||||||
volume->set_volume_rotation(Vec3d::Zero());
|
|
||||||
}
|
|
||||||
else if (selection.is_single_full_instance()) {
|
|
||||||
for (unsigned int idx : selection.get_volume_idxs()){
|
|
||||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(idx));
|
|
||||||
volume->set_instance_rotation(Vec3d::Zero());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
return;
|
|
||||||
|
|
||||||
// Update rotation at the GLVolumes.
|
|
||||||
selection.synchronize_unselected_instances(Selection::SYNC_ROTATION_GENERAL);
|
|
||||||
selection.synchronize_unselected_volumes();
|
|
||||||
// Copy rotation values from GLVolumes into Model (ModelInstance / ModelVolume), trigger background processing.
|
|
||||||
canvas->do_rotate(L("Reset Rotation"));
|
|
||||||
|
|
||||||
UpdateAndShow(true);
|
|
||||||
});
|
|
||||||
return sizer;
|
|
||||||
};
|
|
||||||
line.append_widget(reset_rotation_button);
|
|
||||||
}
|
|
||||||
else if (option_name == "Position") {
|
|
||||||
// Add drop to bed button
|
|
||||||
auto drop_to_bed_button = [=](wxWindow* parent) {
|
|
||||||
auto btn = new ScalableButton(parent, wxID_ANY, ScalableBitmap(parent, "drop_to_bed"));
|
|
||||||
btn->SetToolTip(_(L("Drop to bed")));
|
|
||||||
m_drop_to_bed_button = btn;
|
|
||||||
auto sizer = new wxBoxSizer(wxHORIZONTAL);
|
|
||||||
sizer->Add(btn, wxBU_EXACTFIT);
|
|
||||||
btn->Bind(wxEVT_BUTTON, [=](wxCommandEvent &e) {
|
|
||||||
// ???
|
|
||||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
|
||||||
Selection& selection = canvas->get_selection();
|
|
||||||
|
|
||||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
|
||||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
|
||||||
|
|
||||||
const Geometry::Transformation& instance_trafo = volume->get_instance_transformation();
|
|
||||||
Vec3d diff = m_cache.position - instance_trafo.get_matrix(true).inverse() * Vec3d(0., 0., get_volume_min_z(volume));
|
|
||||||
|
|
||||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _(L("Drop to bed")));
|
|
||||||
change_position_value(0, diff.x());
|
|
||||||
change_position_value(1, diff.y());
|
|
||||||
change_position_value(2, diff.z());
|
|
||||||
}
|
|
||||||
});
|
|
||||||
return sizer;
|
|
||||||
};
|
|
||||||
line.append_widget(drop_to_bed_button);
|
|
||||||
}
|
|
||||||
// Add empty bmp (Its size have to be equal to PrusaLockButton) in front of "Size" option to label alignment
|
|
||||||
else if (option_name == "Size") {
|
|
||||||
line.near_label_widget = [this](wxWindow* parent) {
|
|
||||||
return new wxStaticBitmap(parent, wxID_ANY, wxNullBitmap, wxDefaultPosition,
|
|
||||||
create_scaled_bitmap(m_parent, "one_layer_lock_on.png").GetSize());
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
const std::string lower_name = boost::algorithm::to_lower_copy(option_name);
|
|
||||||
|
|
||||||
for (const char *axis : { "_x", "_y", "_z" }) {
|
|
||||||
if (axis[1] == 'z')
|
|
||||||
def.sidetext = sidetext;
|
|
||||||
Option option = Option(def, lower_name + axis);
|
|
||||||
option.opt.full_width = true;
|
|
||||||
line.append_option(option);
|
|
||||||
}
|
|
||||||
|
|
||||||
return line;
|
|
||||||
};
|
|
||||||
|
|
||||||
// Settings table
|
|
||||||
m_og->sidetext_width = 3;
|
|
||||||
m_og->append_line(add_og_to_object_settings(L("Position"), L("mm")), &m_move_Label);
|
|
||||||
m_og->append_line(add_og_to_object_settings(L("Rotation"), "°"), &m_rotate_Label);
|
|
||||||
m_og->append_line(add_og_to_object_settings(L("Scale"), "%"), &m_scale_Label);
|
|
||||||
m_og->append_line(add_og_to_object_settings(L("Size"), "mm"));
|
|
||||||
|
|
||||||
// call back for a rescale of button "Set uniform scale"
|
|
||||||
m_og->rescale_near_label_widget = [this](wxWindow* win) {
|
|
||||||
// rescale lock icon
|
|
||||||
auto *ctrl = dynamic_cast<LockButton*>(win);
|
|
||||||
if (ctrl != nullptr) {
|
|
||||||
ctrl->msw_rescale();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (win == m_fix_throught_netfab_bitmap)
|
|
||||||
return;
|
|
||||||
|
|
||||||
// rescale "place" of the empty icon (to correct layout of the "Size" and "Scale")
|
|
||||||
if (dynamic_cast<wxStaticBitmap*>(win) != nullptr)
|
|
||||||
win->SetMinSize(create_scaled_bitmap(m_parent, "one_layer_lock_on.png").GetSize());
|
|
||||||
};
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
void ObjectManipulation::Show(const bool show)
|
void ObjectManipulation::Show(const bool show)
|
||||||
{
|
{
|
||||||
if (show != IsShown()) {
|
if (show != IsShown()) {
|
||||||
@ -710,9 +421,9 @@ void ObjectManipulation::Show(const bool show)
|
|||||||
if (show && wxGetApp().get_mode() != comSimple) {
|
if (show && wxGetApp().get_mode() != comSimple) {
|
||||||
// Show the label and the name of the STL in simple mode only.
|
// Show the label and the name of the STL in simple mode only.
|
||||||
// Label "Name: "
|
// Label "Name: "
|
||||||
/*m_og->get_grid_sizer()*/m_main_grid_sizer->Show(size_t(0), false);
|
m_main_grid_sizer->Show(size_t(0), false);
|
||||||
// The actual name of the STL.
|
// The actual name of the STL.
|
||||||
/*m_og->get_grid_sizer()*/m_main_grid_sizer->Show(size_t(1), false);
|
m_main_grid_sizer->Show(size_t(1), false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -833,26 +544,6 @@ void ObjectManipulation::update_if_dirty()
|
|||||||
update_label(m_cache.rotate_label_string, m_new_rotate_label_string, m_rotate_Label);
|
update_label(m_cache.rotate_label_string, m_new_rotate_label_string, m_rotate_Label);
|
||||||
update_label(m_cache.scale_label_string, m_new_scale_label_string, m_scale_Label);
|
update_label(m_cache.scale_label_string, m_new_scale_label_string, m_scale_Label);
|
||||||
|
|
||||||
/*
|
|
||||||
char axis[2] = "x";
|
|
||||||
for (int i = 0; i < 3; ++ i, ++ axis[0]) {
|
|
||||||
auto update = [this, i, &axis](Vec3d &cached, Vec3d &cached_rounded, const char *key, const Vec3d &new_value) {
|
|
||||||
wxString new_text = double_to_string(new_value(i), 2);
|
|
||||||
double new_rounded;
|
|
||||||
new_text.ToDouble(&new_rounded);
|
|
||||||
if (std::abs(cached_rounded(i) - new_rounded) > EPSILON) {
|
|
||||||
cached_rounded(i) = new_rounded;
|
|
||||||
m_og->set_value(std::string(key) + axis, new_text);
|
|
||||||
}
|
|
||||||
cached(i) = new_value(i);
|
|
||||||
};
|
|
||||||
update(m_cache.position, m_cache.position_rounded, "position_", m_new_position);
|
|
||||||
update(m_cache.scale, m_cache.scale_rounded, "scale_", m_new_scale);
|
|
||||||
update(m_cache.size, m_cache.size_rounded, "size_", m_new_size);
|
|
||||||
update(m_cache.rotation, m_cache.rotation_rounded, "rotation_", m_new_rotation);
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
enum ManipulationEditorKey
|
enum ManipulationEditorKey
|
||||||
{
|
{
|
||||||
mePosition = 0,
|
mePosition = 0,
|
||||||
@ -1007,17 +698,10 @@ void ObjectManipulation::update_mirror_buttons_visibility()
|
|||||||
#ifndef __APPLE__
|
#ifndef __APPLE__
|
||||||
void ObjectManipulation::emulate_kill_focus()
|
void ObjectManipulation::emulate_kill_focus()
|
||||||
{
|
{
|
||||||
if (m_focused_option.empty())
|
if (!m_focused_editor)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// we need to use a copy because the value of m_focused_option is modified inside on_change() and on_fill_empty_value()
|
m_focused_editor->kill_focus(this);
|
||||||
std::string option = m_focused_option;
|
|
||||||
|
|
||||||
// see TextCtrl::propagate_value()
|
|
||||||
if (static_cast<wxTextCtrl*>(m_og->get_fieldc(option, 0)->getWindow())->GetValue().empty())
|
|
||||||
on_fill_empty_value(option);
|
|
||||||
else
|
|
||||||
on_change(option, 0);
|
|
||||||
}
|
}
|
||||||
#endif // __APPLE__
|
#endif // __APPLE__
|
||||||
|
|
||||||
@ -1156,40 +840,6 @@ void ObjectManipulation::do_scale(int axis, const Vec3d &scale) const
|
|||||||
wxGetApp().plater()->canvas3D()->do_scale(L("Set Scale"));
|
wxGetApp().plater()->canvas3D()->do_scale(L("Set Scale"));
|
||||||
}
|
}
|
||||||
|
|
||||||
void ObjectManipulation::on_change(t_config_option_key opt_key, const boost::any& value)
|
|
||||||
{
|
|
||||||
Field* field = m_og->get_field(opt_key);
|
|
||||||
bool enter_pressed = (field != nullptr) && field->get_enter_pressed();
|
|
||||||
if (!enter_pressed)
|
|
||||||
{
|
|
||||||
// if the change does not come from the user pressing the ENTER key
|
|
||||||
// we need to hide the visual hints in 3D scene
|
|
||||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(opt_key, false);
|
|
||||||
|
|
||||||
#ifndef __APPLE__
|
|
||||||
m_focused_option = "";
|
|
||||||
#endif // __APPLE__
|
|
||||||
}
|
|
||||||
else
|
|
||||||
// if the change comes from the user pressing the ENTER key, restore the key state
|
|
||||||
field->set_enter_pressed(false);
|
|
||||||
|
|
||||||
if (!m_cache.is_valid())
|
|
||||||
return;
|
|
||||||
|
|
||||||
int axis = opt_key.back() - 'x';
|
|
||||||
double new_value = boost::any_cast<double>(m_og->get_value(opt_key));
|
|
||||||
|
|
||||||
if (boost::starts_with(opt_key, "position_"))
|
|
||||||
change_position_value(axis, new_value);
|
|
||||||
else if (boost::starts_with(opt_key, "rotation_"))
|
|
||||||
change_rotation_value(axis, new_value);
|
|
||||||
else if (boost::starts_with(opt_key, "scale_"))
|
|
||||||
change_scale_value(axis, new_value);
|
|
||||||
else if (boost::starts_with(opt_key, "size_"))
|
|
||||||
change_size_value(axis, new_value);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ObjectManipulation::on_change(const std::string& opt_key, int axis, double new_value)
|
void ObjectManipulation::on_change(const std::string& opt_key, int axis, double new_value)
|
||||||
{
|
{
|
||||||
if (!m_cache.is_valid())
|
if (!m_cache.is_valid())
|
||||||
@ -1205,42 +855,6 @@ void ObjectManipulation::on_change(const std::string& opt_key, int axis, double
|
|||||||
change_size_value(axis, new_value);
|
change_size_value(axis, new_value);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ObjectManipulation::on_fill_empty_value(const std::string& opt_key)
|
|
||||||
{
|
|
||||||
// needed to hide the visual hints in 3D scene
|
|
||||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(opt_key, false);
|
|
||||||
#ifndef __APPLE__
|
|
||||||
m_focused_option = "";
|
|
||||||
#endif // __APPLE__
|
|
||||||
|
|
||||||
if (!m_cache.is_valid())
|
|
||||||
return;
|
|
||||||
|
|
||||||
const Vec3d *vec = nullptr;
|
|
||||||
Vec3d *rounded = nullptr;
|
|
||||||
if (boost::starts_with(opt_key, "position_")) {
|
|
||||||
vec = &m_cache.position;
|
|
||||||
rounded = &m_cache.position_rounded;
|
|
||||||
} else if (boost::starts_with(opt_key, "rotation_")) {
|
|
||||||
vec = &m_cache.rotation;
|
|
||||||
rounded = &m_cache.rotation_rounded;
|
|
||||||
} else if (boost::starts_with(opt_key, "scale_")) {
|
|
||||||
vec = &m_cache.scale;
|
|
||||||
rounded = &m_cache.scale_rounded;
|
|
||||||
} else if (boost::starts_with(opt_key, "size_")) {
|
|
||||||
vec = &m_cache.size;
|
|
||||||
rounded = &m_cache.size_rounded;
|
|
||||||
} else
|
|
||||||
assert(false);
|
|
||||||
|
|
||||||
if (vec != nullptr) {
|
|
||||||
int axis = opt_key.back() - 'x';
|
|
||||||
wxString new_text = double_to_string((*vec)(axis));
|
|
||||||
m_og->set_value(opt_key, new_text);
|
|
||||||
new_text.ToDouble(&(*rounded)(axis));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void ObjectManipulation::set_uniform_scaling(const bool new_value)
|
void ObjectManipulation::set_uniform_scaling(const bool new_value)
|
||||||
{
|
{
|
||||||
const Selection &selection = wxGetApp().plater()->canvas3D()->get_selection();
|
const Selection &selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||||
@ -1338,43 +952,25 @@ ManipulationEditor::ManipulationEditor(ObjectManipulation* parent,
|
|||||||
parent->on_change(m_opt_key, m_axis, get_value());
|
parent->on_change(m_opt_key, m_axis, get_value());
|
||||||
}, this->GetId());
|
}, this->GetId());
|
||||||
|
|
||||||
this->Bind(wxEVT_KILL_FOCUS, [this, parent/*, edit_fn*/](wxFocusEvent& e)
|
this->Bind(wxEVT_KILL_FOCUS, [this, parent](wxFocusEvent& e)
|
||||||
{
|
{
|
||||||
if (!m_enter_pressed) {
|
parent->set_focused_editor(nullptr);
|
||||||
parent->on_change(m_opt_key, m_axis, get_value());
|
|
||||||
|
|
||||||
// if the change does not come from the user pressing the ENTER key
|
if (!m_enter_pressed)
|
||||||
// we need to hide the visual hints in 3D scene
|
kill_focus(parent);
|
||||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(m_full_opt_name, false);
|
|
||||||
// #ifndef __WXGTK__
|
|
||||||
// /* Update data for next editor selection.
|
|
||||||
// * But under GTK it looks like there is no information about selected control at e.GetWindow(),
|
|
||||||
// * so we'll take it from wxEVT_LEFT_DOWN event
|
|
||||||
// * */
|
|
||||||
// LayerRangeEditor* new_editor = dynamic_cast<LayerRangeEditor*>(e.GetWindow());
|
|
||||||
// if (new_editor)
|
|
||||||
// new_editor->set_focus_data();
|
|
||||||
// #endif // not __WXGTK__
|
|
||||||
}
|
|
||||||
|
|
||||||
e.Skip();
|
e.Skip();
|
||||||
}, this->GetId());
|
}, this->GetId());
|
||||||
|
|
||||||
this->Bind(wxEVT_SET_FOCUS, [this](wxFocusEvent& e)
|
this->Bind(wxEVT_SET_FOCUS, [this, parent](wxFocusEvent& e)
|
||||||
{
|
{
|
||||||
|
parent->set_focused_editor(this);
|
||||||
|
|
||||||
// needed to show the visual hints in 3D scene
|
// needed to show the visual hints in 3D scene
|
||||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(m_full_opt_name, true);
|
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(m_full_opt_name, true);
|
||||||
e.Skip();
|
e.Skip();
|
||||||
}, this->GetId());
|
}, this->GetId());
|
||||||
|
|
||||||
// #ifdef __WXGTK__ // Workaround! To take information about selectable range
|
|
||||||
// this->Bind(wxEVT_LEFT_DOWN, [this](wxEvent& e)
|
|
||||||
// {
|
|
||||||
// set_focus_data();
|
|
||||||
// e.Skip();
|
|
||||||
// }, this->GetId());
|
|
||||||
// #endif //__WXGTK__
|
|
||||||
|
|
||||||
this->Bind(wxEVT_CHAR, ([this](wxKeyEvent& event)
|
this->Bind(wxEVT_CHAR, ([this](wxKeyEvent& event)
|
||||||
{
|
{
|
||||||
// select all text using Ctrl+A
|
// select all text using Ctrl+A
|
||||||
@ -1417,5 +1013,14 @@ void ManipulationEditor::set_value(const wxString& new_value)
|
|||||||
SetValue(m_valid_value);
|
SetValue(m_valid_value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ManipulationEditor::kill_focus(ObjectManipulation* parent)
|
||||||
|
{
|
||||||
|
parent->on_change(m_opt_key, m_axis, get_value());
|
||||||
|
|
||||||
|
// if the change does not come from the user pressing the ENTER key
|
||||||
|
// we need to hide the visual hints in 3D scene
|
||||||
|
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(m_full_opt_name, false);
|
||||||
|
}
|
||||||
|
|
||||||
} //namespace GUI
|
} //namespace GUI
|
||||||
} //namespace Slic3r
|
} //namespace Slic3r
|
||||||
|
@ -32,6 +32,7 @@ public:
|
|||||||
|
|
||||||
void msw_rescale();
|
void msw_rescale();
|
||||||
void set_value(const wxString& new_value);
|
void set_value(const wxString& new_value);
|
||||||
|
void kill_focus(ObjectManipulation *parent);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
double get_value();
|
double get_value();
|
||||||
@ -118,7 +119,7 @@ class ObjectManipulation : public OG_Settings
|
|||||||
|
|
||||||
#ifndef __APPLE__
|
#ifndef __APPLE__
|
||||||
// Currently focused option name (empty if none)
|
// Currently focused option name (empty if none)
|
||||||
std::string m_focused_option;
|
ManipulationEditor* m_focused_editor {nullptr};
|
||||||
#endif // __APPLE__
|
#endif // __APPLE__
|
||||||
|
|
||||||
wxFlexGridSizer* m_main_grid_sizer;
|
wxFlexGridSizer* m_main_grid_sizer;
|
||||||
@ -160,6 +161,7 @@ public:
|
|||||||
void update_warning_icon_state(const wxString& tooltip);
|
void update_warning_icon_state(const wxString& tooltip);
|
||||||
void msw_rescale();
|
void msw_rescale();
|
||||||
void on_change(const std::string& opt_key, int axis, double new_value);
|
void on_change(const std::string& opt_key, int axis, double new_value);
|
||||||
|
void set_focused_editor(ManipulationEditor* focused_editor) { m_focused_editor = focused_editor; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void reset_settings_value();
|
void reset_settings_value();
|
||||||
@ -176,9 +178,6 @@ private:
|
|||||||
void change_scale_value(int axis, double value);
|
void change_scale_value(int axis, double value);
|
||||||
void change_size_value(int axis, double value);
|
void change_size_value(int axis, double value);
|
||||||
void do_scale(int axis, const Vec3d &scale) const;
|
void do_scale(int axis, const Vec3d &scale) const;
|
||||||
|
|
||||||
void on_change(t_config_option_key opt_key, const boost::any& value);
|
|
||||||
void on_fill_empty_value(const std::string& opt_key);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
}}
|
}}
|
||||||
|
Loading…
Reference in New Issue
Block a user