prusa3d / PrusaSlicer

G-code generator for 3D printers (RepRap, Makerbot, Ultimaker etc.)
https://www.prusa3d.com/prusaslicer/
GNU Affero General Public License v3.0
7.75k stars 1.93k forks source link

Calculation relation between spacing and density of honeycomb filling #7675

Closed Ccaomei closed 2 years ago

Ccaomei commented 2 years ago

Hello everyone, I want to know the calculation relationship between the spacing and density of honeycomb filling, and where to set the offset distance between the filling graph and the polygon, and what is the unit of the coordinates of the filled polygon. I hope you can give me your advice, thank you very much.

n8bot commented 2 years ago

https://github.com/prusa3d/PrusaSlicer/blob/a554f1fb089ccbc6fee995571091054703ca181d/src/libslic3r/Fill/FillHoneycomb.cpp#L16-L33

Ccaomei commented 2 years ago

https://github.com/prusa3d/PrusaSlicer/blob/a554f1fb089ccbc6fee995571091054703ca181d/src/libslic3r/Fill/FillHoneycomb.cpp#L16-L33

@n8bot hi,What are the units of polygon coordinates?Do you have documentation for information about units。thanks !

n8bot commented 2 years ago

To be honest, I have no more information. I've never needed to change the honeycomb. I assume the coordinates are in mm, but they may be scaled mm, which would be x/0.000001, or a million times larger.

Ccaomei commented 2 years ago

To be honest, I have no more information. I've never needed to change the honeycomb. I assume the coordinates are in mm, but they may be scaled mm, which would be x/0.000001, or a million times larger.

@n8bot , hi , In the demo, I set spacing and density, but the density of the filling graph is not the specified density. Can you explain the relationship between spacing and density and the offset of the filling graph?

Ccaomei commented 2 years ago

To be honest, I have no more information. I've never needed to change the honeycomb. I assume the coordinates are in mm, but they may be scaled mm, which would be x/0.000001, or a million times larger.

@n8bot , hi , In the demo, I set spacing and density, but the density of the filling graph is not the specified density. Can you explain the relationship between spacing and density and the offset of the filling graph?

n8bot commented 2 years ago

I'm no expert by any means, but I suspect you might be forgetting to use scaled units (they will never have a decimal place. Units are scaled to integer-like values. 1,000,000x larger than the "real" value.)

The distance, etc is taken from the const FillParams &params, that are sent as an argument to the _fill_surface_single().

https://github.com/prusa3d/PrusaSlicer/blob/a554f1fb089ccbc6fee995571091054703ca181d/src/libslic3r/Fill/FillBase.hpp#L33-L60

n8bot commented 2 years ago

But, the spacing is derived from the Fill -- which is what should be calling this _fill_surface_single.

So, without knowing more details about what you're doing it's difficult to help you. It all changes depending on what and where you are trying to do it.

n8bot commented 2 years ago

I suggest you forget about the function we've been talking about, and look how the support material uses the fillers. It seems much easier to adapt as needed:

https://github.com/prusa3d/PrusaSlicer/blob/934611206d8ab360ccabe9f27c7d6d72f3fb807e/src/libslic3r/SupportMaterial.cpp#L3234-L3254

https://github.com/prusa3d/PrusaSlicer/blob/481def3205182193140c6186420fe97adbda8abc/src/libslic3r/Fill/FillBase.cpp#L81-L95

Ccaomei commented 2 years ago

1

@n8bot Hi, I want to refer to demo, write an interface, directly pass polygons, see the filling effect. I'd like to ask some questions: Fill_params. density = float(filler->Spacing / 50.0);What does spacing mean, and what does 50.0 mean? 2, is there any parameter to set the filling line width;

  1. The relationship between filling density and filling line width; Help to answer again, extremely grateful!!
n8bot commented 2 years ago
  1. spacing is the distance, center-to-center, between two lines, if they are printed right next to each other.
    • The 50 is just a value used to make a density of 0.1, based on the testing scenario 5 mm spacing.
  2. The line width is basically the same as the spacing.
  3. The density is related to the spacing. The spacing relates closely to the line width.

The line width is really just an idea, though. The polyline coordinates are based on the centerlines of the extrusions. The height and width of the lines are basically metadata that is used in other places. Think about the gcode output that PS is doing: it defines the X, Y, and Z coordinates of the polylines explicitly. But the thickness in height and width is determined implicitly by the extrusion amounts. The width and height are essentially decoupled from the coordinates of the path.

[Edit: I forgot to mention -- the Flow is where the line width is determined, essentially.]

Ccaomei commented 2 years ago

9 @n8bot ,hi,I set spacing=5mm and density=0.5. The SVG image generated at this density, with the padding line width set to 5mm, should have 1:1 padding line width and padding line spacing, but the resulting SVG image looks like this, what am I wrong?

std::unique_ptr filler( Slic3r::Fill::new_from_type("alignedrectilinear")); filler->angle = float(-(PI)/2.0); FillParams fill_params; filler->spacing = 5; //5 fill_params.dont_adjust = true; //fill_params.endpoints_overlap = false; fill_params.density = 0.5;

Slic3r::Points ps; ps.push_back(Point(0, 0)); ps.push_back(Point(50000000, 0)); ps.push_back(Point(50000000, 50000000)); ps.push_back(Point(0, 50000000)); Slic3r::Polygon p1(ps); ttp.push_back(p1);

    ClipperLib::PolyFillType fill_type =  ClipperLib::pftEvenOdd;  // pftNonZero;
    Slic3r::ExPolygons       xxp       = union_ex(ttp, fill_type);
            filler->angle = float(angle);
            BoundingBox bbox = get_extents(xxp);
            printf("xxp.size()=%d\n", xxp.size());
            char buf[128];
            sprintf(buf, "e:\\data\\temp\\square_with_holes_xxp_xx.svg");
            SVG svg(buf, bbox);
            svg.draw_outline(xxp, "black", "blue", 1*1000*1000);
            for (int i = 0; i < xxp.size(); i++) 
            {
                Slic3r::Polylines paths = test(xxp[i]);
                svg.draw(paths, "red", 0.5*1000*1000);
            }
            svg.Close();
n8bot commented 2 years ago

I'm not sure what information you need.

The spacing + density define how far apart those lines are.

The width of the lines is not set or relevant to these tests. They are testing the infill pattern, not the extrusion width. No extrusion width is used in these tests. If you want the SVG output lines to be different, you will have to edit the SVG. If the SVG is using a stroke value, this will be easy. Simply increase the stroke to your liking.

But this is getting farther from my knowledge of PrusaSlicer, and into the realm of general knowledge.

Ccaomei commented 2 years ago

I'm not sure what information you need.

The spacing + density define how far apart those lines are.

The width of the lines is not set or relevant to these tests. They are testing the infill pattern, not the extrusion width. No extrusion width is used in these tests. If you want the SVG output lines to be different, you will have to edit the SVG. If the SVG is using a stroke value, this will be easy. Simply increase the stroke to your liking.

But this is getting farther from my knowledge of PrusaSlicer, and into the realm of general knowledge.

@n8bot ,hi,I want to express that the SVG diagram I got is not consistent with the density I set. I want to know what is wrong and I hope to get your help. The SVG diagram and code have been pasted, please help to have a look.Thank you very much!

n8bot commented 2 years ago

The width of the SVG lines does not relate to anything, even if you multiply them by a million it seems.

I have sliced something in the software with 0.5 mm spacing, and 50% density, which should provide a similar result to yours. When I scale it and overlay it against your SVG, we can see what is happening and how the line thickness of the SVG is misleading.

image

image

n8bot commented 2 years ago

The black rectangle is defining only the inner part, there is no line width accounted for on its edge. The yellow you see in the overlaid image is the perimeters -- as you see, the black line of the rectangle in your SVG is on the edge of the inside of the perimeter.

Ccaomei commented 2 years ago

@n8bot ,hi,“ filler->angle = float(-(PI)/2.0); ” ,May I ask how to set the Angle so that I can set the filling Angle from 0 degrees to 360 degrees?

n8bot commented 2 years ago

Yes. The angle is set in radians. So, if I remember correctly, a value of pi is 180 degrees.

Ccaomei commented 2 years ago

@n8bot ,hi, I would like to ask you another question. Where is the parameter "fill/contour overlap" set in the fill module?

n8bot commented 2 years ago

The overlap is done differently depending on the infill type. I like the way rectilinear does it, with an ExPolygonWithOffset

https://github.com/prusa3d/PrusaSlicer/blob/a6d280bd9ecc131ff0589a6246be1ecdea0fb0a7/src/libslic3r/Fill/FillRectilinear.cpp#L3020-L3042

It is essentially just an offset of the input polygon for the fill.

lukasmatena commented 2 years ago

Closing. Feel free to continue in the discussion, but it clutters the (already a bit long) list of open issues.

Ccaomei commented 2 years ago

@n8bot, hi, I do not understand the use of "ExPolygonWithOffset", could you please give me a demo to use it to offset the filling line? If it is honeycomb filling, how to offset the filling line? Looking forward to your reply. thank you

n8bot commented 2 years ago

For the honeycomb infill. the input ExPolygon itself is offet.

See line 84: https://github.com/prusa3d/PrusaSlicer/blob/1dffc40f324a9bf2361b55c0f4e227508e25f388/src/libslic3r/Fill/FillBase.cpp#L81-L95

The ExPolygonWithOffset is a special type that contains information about offset polygons, which seems made for the purpose of accounting for the overlap of infill, but is only used for rectilinear.