Cut WIP:
* ObjectDataViewModel: Respect to the volume id, when adding the new volume to the object * 3mf : Save/Load info about connectors
This commit is contained in:
parent
0201a5055a
commit
d1c871758b
@ -409,6 +409,19 @@ namespace Slic3r {
|
||||
VolumeMetadataList volumes;
|
||||
};
|
||||
|
||||
struct CutObjectInfo
|
||||
{
|
||||
struct Connector
|
||||
{
|
||||
int volume_id;
|
||||
int type;
|
||||
float r_tolerance;
|
||||
float h_tolerance;
|
||||
};
|
||||
CutObjectBase id;
|
||||
std::vector<Connector> connectors;
|
||||
};
|
||||
|
||||
// Map from a 1 based 3MF object ID to a 0 based ModelObject index inside m_model->objects.
|
||||
typedef std::map<int, int> IdToModelObjectMap;
|
||||
typedef std::map<int, ComponentsList> IdToAliasesMap;
|
||||
@ -417,7 +430,7 @@ namespace Slic3r {
|
||||
typedef std::map<int, Geometry> IdToGeometryMap;
|
||||
typedef std::map<int, std::vector<coordf_t>> IdToLayerHeightsProfileMap;
|
||||
typedef std::map<int, t_layer_config_ranges> IdToLayerConfigRangesMap;
|
||||
typedef std::map<int, CutObjectBase> IdToCutObjectIdMap;
|
||||
typedef std::map<int, CutObjectInfo> IdToCutObjectInfoMap;
|
||||
typedef std::map<int, std::vector<sla::SupportPoint>> IdToSlaSupportPointsMap;
|
||||
typedef std::map<int, std::vector<sla::DrainHole>> IdToSlaDrainHolesMap;
|
||||
|
||||
@ -445,7 +458,7 @@ namespace Slic3r {
|
||||
IdToGeometryMap m_geometries;
|
||||
CurrentConfig m_curr_config;
|
||||
IdToMetadataMap m_objects_metadata;
|
||||
IdToCutObjectIdMap m_cut_object_ids;
|
||||
IdToCutObjectInfoMap m_cut_object_infos;
|
||||
IdToLayerHeightsProfileMap m_layer_heights_profiles;
|
||||
IdToLayerConfigRangesMap m_layer_config_ranges;
|
||||
IdToSlaSupportPointsMap m_sla_support_points;
|
||||
@ -774,11 +787,6 @@ namespace Slic3r {
|
||||
return false;
|
||||
}
|
||||
|
||||
// m_cut_object_ids are indexed by a 1 based model object index.
|
||||
IdToCutObjectIdMap::iterator cut_object_id = m_cut_object_ids.find(object.second + 1);
|
||||
if (cut_object_id != m_cut_object_ids.end())
|
||||
model_object->cut_id = std::move(cut_object_id->second);
|
||||
|
||||
// m_layer_heights_profiles are indexed by a 1 based model object index.
|
||||
IdToLayerHeightsProfileMap::iterator obj_layer_heights_profile = m_layer_heights_profiles.find(object.second + 1);
|
||||
if (obj_layer_heights_profile != m_layer_heights_profiles.end())
|
||||
@ -831,6 +839,19 @@ namespace Slic3r {
|
||||
|
||||
if (!_generate_volumes(*model_object, obj_geometry->second, *volumes_ptr, config_substitutions))
|
||||
return false;
|
||||
|
||||
// Apply cut information for object if any was loaded
|
||||
// m_cut_object_ids are indexed by a 1 based model object index.
|
||||
IdToCutObjectInfoMap::iterator cut_object_info = m_cut_object_infos.find(object.second + 1);
|
||||
if (cut_object_info != m_cut_object_infos.end()) {
|
||||
model_object->cut_id = cut_object_info->second.id;
|
||||
|
||||
for (auto connector : cut_object_info->second.connectors) {
|
||||
assert(0 <= connector.volume_id && connector.volume_id <= int(model_object->volumes.size()));
|
||||
model_object->volumes[connector.volume_id]->cut_info =
|
||||
ModelVolume::CutInfo(CutConnectorType(connector.type), connector.r_tolerance, connector.h_tolerance, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// If instances contain a single volume, the volume offset should be 0,0,0
|
||||
@ -979,22 +1000,39 @@ namespace Slic3r {
|
||||
continue;
|
||||
}
|
||||
|
||||
IdToCutObjectIdMap::iterator object_item = m_cut_object_ids.find(obj_idx);
|
||||
if (object_item != m_cut_object_ids.end()) {
|
||||
IdToCutObjectInfoMap::iterator object_item = m_cut_object_infos.find(obj_idx);
|
||||
if (object_item != m_cut_object_infos.end()) {
|
||||
add_error("Found duplicated cut_object_id");
|
||||
continue;
|
||||
}
|
||||
|
||||
for (const auto& obj_cut_id : object_tree) {
|
||||
if (obj_cut_id.first != "cut_id")
|
||||
continue;
|
||||
pt::ptree cut_id_tree = obj_cut_id.second;
|
||||
ObjectID obj_id(cut_id_tree.get<size_t>("<xmlattr>.id"));
|
||||
CutObjectBase cut_id(ObjectID(cut_id_tree.get<size_t>("<xmlattr>.id")),
|
||||
cut_id_tree.get<size_t>("<xmlattr>.check_sum"),
|
||||
cut_id_tree.get<size_t>("<xmlattr>.connectors_cnt"));
|
||||
m_cut_object_ids.insert({ obj_idx, std::move(cut_id) });
|
||||
CutObjectBase cut_id;
|
||||
std::vector<CutObjectInfo::Connector> connectors;
|
||||
|
||||
for (const auto& obj_cut_info : object_tree) {
|
||||
if (obj_cut_info.first == "cut_id") {
|
||||
pt::ptree cut_id_tree = obj_cut_info.second;
|
||||
cut_id = CutObjectBase(ObjectID( cut_id_tree.get<size_t>("<xmlattr>.id")),
|
||||
cut_id_tree.get<size_t>("<xmlattr>.check_sum"),
|
||||
cut_id_tree.get<size_t>("<xmlattr>.connectors_cnt"));
|
||||
}
|
||||
if (obj_cut_info.first == "connectors") {
|
||||
pt::ptree cut_connectors_tree = obj_cut_info.second;
|
||||
for (const auto& cut_connector : cut_connectors_tree) {
|
||||
if (cut_connector.first != "connector")
|
||||
continue;
|
||||
pt::ptree connector_tree = cut_connector.second;
|
||||
CutObjectInfo::Connector connector = {connector_tree.get<int>("<xmlattr>.volume_id"),
|
||||
connector_tree.get<int>("<xmlattr>.type"),
|
||||
connector_tree.get<float>("<xmlattr>.r_tolerance"),
|
||||
connector_tree.get<float>("<xmlattr>.h_tolerance")};
|
||||
connectors.emplace_back(connector);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
CutObjectInfo cut_info {cut_id, connectors};
|
||||
m_cut_object_infos.insert({ obj_idx, cut_info });
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -2865,6 +2903,18 @@ namespace Slic3r {
|
||||
cut_id_tree.put("<xmlattr>.id", object->cut_id.id().id);
|
||||
cut_id_tree.put("<xmlattr>.check_sum", object->cut_id.check_sum());
|
||||
cut_id_tree.put("<xmlattr>.connectors_cnt", object->cut_id.connectors_cnt());
|
||||
|
||||
int volume_idx = -1;
|
||||
for (const ModelVolume* volume : object->volumes) {
|
||||
++volume_idx;
|
||||
if (volume->is_cut_connector()) {
|
||||
pt::ptree& connectors_tree = obj_tree.add("connectors.connector", "");
|
||||
connectors_tree.put("<xmlattr>.volume_id", volume_idx);
|
||||
connectors_tree.put("<xmlattr>.type", int(volume->cut_info.connector_type));
|
||||
connectors_tree.put("<xmlattr>.r_tolerance", volume->cut_info.radius_tolerance);
|
||||
connectors_tree.put("<xmlattr>.h_tolerance", volume->cut_info.height_tolerance);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!tree.empty()) {
|
||||
@ -2876,6 +2926,10 @@ namespace Slic3r {
|
||||
boost::replace_all(out, "><object", ">\n <object");
|
||||
boost::replace_all(out, "><cut_id", ">\n <cut_id");
|
||||
boost::replace_all(out, "></cut_id>", ">\n </cut_id>");
|
||||
boost::replace_all(out, "><connectors", ">\n <connectors");
|
||||
boost::replace_all(out, "></connectors>", ">\n </connectors>");
|
||||
boost::replace_all(out, "><connector", ">\n <connector");
|
||||
boost::replace_all(out, "></connector>", ">\n </connector>");
|
||||
boost::replace_all(out, "></object>", ">\n </object>");
|
||||
// OR just
|
||||
boost::replace_all(out, "><", ">\n<");
|
||||
|
@ -730,9 +730,9 @@ public:
|
||||
float height_tolerance{ 0.f };// [0.f : 1.f]
|
||||
|
||||
CutInfo() = default;
|
||||
CutInfo(CutConnectorType type, float rad_tolerance, float h_tolerance) :
|
||||
CutInfo(CutConnectorType type, float rad_tolerance, float h_tolerance, bool processed = false) :
|
||||
is_connector(true),
|
||||
is_processed(false),
|
||||
is_processed(processed),
|
||||
connector_type(type),
|
||||
radius_tolerance(rad_tolerance),
|
||||
height_tolerance(h_tolerance)
|
||||
|
@ -288,6 +288,9 @@ public:
|
||||
void changed_object(const int obj_idx = -1) const;
|
||||
void part_selection_changed();
|
||||
|
||||
// Add object's volumes to the list
|
||||
// Return selected items, if add_to_selection is defined
|
||||
wxDataViewItemArray add_volumes_to_object_in_list(size_t obj_idx, std::function<bool(const ModelVolume*)> add_to_selection = nullptr);
|
||||
// Add object to the list
|
||||
void add_object_to_list(size_t obj_idx, bool call_selection_changed = true);
|
||||
// Delete object from the list
|
||||
@ -392,7 +395,7 @@ public:
|
||||
void toggle_printable_state();
|
||||
|
||||
void set_extruder_for_selected_items(const int extruder) const ;
|
||||
wxDataViewItemArray reorder_volumes_and_get_selection(int obj_idx, std::function<bool(const ModelVolume*)> add_to_selection = nullptr);
|
||||
wxDataViewItemArray reorder_volumes_and_get_selection(size_t obj_idx, std::function<bool(const ModelVolume*)> add_to_selection = nullptr);
|
||||
void apply_volumes_order();
|
||||
bool has_paint_on_segmentation();
|
||||
|
||||
|
@ -373,13 +373,12 @@ void ObjectDataViewModel::UpdateBitmapForNode(ObjectDataViewModelNode* node, con
|
||||
UpdateBitmapForNode(node);
|
||||
}
|
||||
|
||||
wxDataViewItem ObjectDataViewModel::Add(const wxString &name,
|
||||
const int extruder,
|
||||
wxDataViewItem ObjectDataViewModel::AddObject(const wxString &name,
|
||||
const wxString& extruder,
|
||||
const std::string& warning_icon_name,
|
||||
const bool has_lock)
|
||||
{
|
||||
const wxString extruder_str = extruder == 0 ? _L("default") : wxString::Format("%d", extruder);
|
||||
auto root = new ObjectDataViewModelNode(name, extruder_str);
|
||||
auto root = new ObjectDataViewModelNode(name, extruder);
|
||||
// Add warning icon if detected auto-repaire
|
||||
UpdateBitmapForNode(root, warning_icon_name, has_lock);
|
||||
|
||||
@ -394,37 +393,20 @@ wxDataViewItem ObjectDataViewModel::Add(const wxString &name,
|
||||
|
||||
wxDataViewItem ObjectDataViewModel::AddVolumeChild( const wxDataViewItem &parent_item,
|
||||
const wxString &name,
|
||||
const int volume_idx,
|
||||
const Slic3r::ModelVolumeType volume_type,
|
||||
const std::string& warning_icon_name/* = std::string()*/,
|
||||
const int extruder/* = 0*/,
|
||||
const bool create_frst_child/* = true*/)
|
||||
const std::string& warning_icon_name,
|
||||
const wxString& extruder)
|
||||
{
|
||||
ObjectDataViewModelNode *root = static_cast<ObjectDataViewModelNode*>(parent_item.GetID());
|
||||
if (!root) return wxDataViewItem(0);
|
||||
|
||||
wxString extruder_str = extruder == 0 ? _(L("default")) : wxString::Format("%d", extruder);
|
||||
|
||||
// get insertion position according to the existed Layers and/or Instances Items
|
||||
int insert_position = get_root_idx(root, itLayerRoot);
|
||||
if (insert_position < 0)
|
||||
insert_position = get_root_idx(root, itInstanceRoot);
|
||||
|
||||
if (create_frst_child && root->m_volumes_cnt == 0)
|
||||
{
|
||||
const Slic3r::ModelVolumeType type = Slic3r::ModelVolumeType::MODEL_PART;
|
||||
const auto node = new ObjectDataViewModelNode(root, root->m_name, type, extruder_str, 0);
|
||||
UpdateBitmapForNode(node, root->warning_icon_name(), root->has_lock());
|
||||
|
||||
insert_position < 0 ? root->Append(node) : root->Insert(node, insert_position);
|
||||
// notify control
|
||||
const wxDataViewItem child((void*)node);
|
||||
ItemAdded(parent_item, child);
|
||||
|
||||
root->m_volumes_cnt++;
|
||||
if (insert_position >= 0) insert_position++;
|
||||
}
|
||||
|
||||
const auto node = new ObjectDataViewModelNode(root, name, volume_type, extruder_str, root->m_volumes_cnt);
|
||||
const auto node = new ObjectDataViewModelNode(root, name, volume_type, extruder, volume_idx);
|
||||
UpdateBitmapForNode(node, warning_icon_name, root->has_lock() && volume_type < ModelVolumeType::PARAMETER_MODIFIER);
|
||||
insert_position < 0 ? root->Append(node) : root->Insert(node, insert_position);
|
||||
|
||||
@ -631,14 +613,12 @@ wxDataViewItem ObjectDataViewModel::AddLayersRoot(const wxDataViewItem &parent_i
|
||||
|
||||
wxDataViewItem ObjectDataViewModel::AddLayersChild(const wxDataViewItem &parent_item,
|
||||
const t_layer_height_range& layer_range,
|
||||
const int extruder/* = 0*/,
|
||||
const wxString& extruder,
|
||||
const int index /* = -1*/)
|
||||
{
|
||||
ObjectDataViewModelNode *parent_node = static_cast<ObjectDataViewModelNode*>(parent_item.GetID());
|
||||
if (!parent_node) return wxDataViewItem(0);
|
||||
|
||||
wxString extruder_str = extruder == 0 ? _(L("default")) : wxString::Format("%d", extruder);
|
||||
|
||||
// get LayerRoot node
|
||||
ObjectDataViewModelNode *layer_root_node;
|
||||
wxDataViewItem layer_root_item;
|
||||
@ -655,7 +635,7 @@ wxDataViewItem ObjectDataViewModel::AddLayersChild(const wxDataViewItem &parent_
|
||||
}
|
||||
|
||||
// Add layer node
|
||||
ObjectDataViewModelNode *layer_node = new ObjectDataViewModelNode(layer_root_node, layer_range, index, extruder_str);
|
||||
ObjectDataViewModelNode *layer_node = new ObjectDataViewModelNode(layer_root_node, layer_range, index, extruder);
|
||||
if (index < 0)
|
||||
layer_root_node->Append(layer_node);
|
||||
else
|
||||
|
@ -271,16 +271,16 @@ public:
|
||||
ObjectDataViewModel();
|
||||
~ObjectDataViewModel();
|
||||
|
||||
wxDataViewItem Add( const wxString &name,
|
||||
const int extruder,
|
||||
wxDataViewItem AddObject( const wxString &name,
|
||||
const wxString& extruder,
|
||||
const std::string& warning_icon_name,
|
||||
const bool has_lock);
|
||||
wxDataViewItem AddVolumeChild( const wxDataViewItem &parent_item,
|
||||
const wxString &name,
|
||||
const int volume_idx,
|
||||
const Slic3r::ModelVolumeType volume_type,
|
||||
const std::string& warning_icon_name = std::string(),
|
||||
const int extruder = 0,
|
||||
const bool create_frst_child = true);
|
||||
const std::string& warning_icon_name,
|
||||
const wxString& extruder);
|
||||
wxDataViewItem AddSettingsChild(const wxDataViewItem &parent_item);
|
||||
wxDataViewItem AddInfoChild(const wxDataViewItem &parent_item, InfoItemType info_type);
|
||||
wxDataViewItem AddInstanceChild(const wxDataViewItem &parent_item, size_t num);
|
||||
@ -288,7 +288,7 @@ public:
|
||||
wxDataViewItem AddLayersRoot(const wxDataViewItem &parent_item);
|
||||
wxDataViewItem AddLayersChild( const wxDataViewItem &parent_item,
|
||||
const t_layer_height_range& layer_range,
|
||||
const int extruder = 0,
|
||||
const wxString& extruder,
|
||||
const int index = -1);
|
||||
size_t GetItemIndexForFirstVolume(ObjectDataViewModelNode* node_parent);
|
||||
wxDataViewItem Delete(const wxDataViewItem &item);
|
||||
|
Loading…
Reference in New Issue
Block a user