discuss@lists.openscad.org

OpenSCAD general discussion Mailing-list

View all threads

Non-Linear Transformations

T
Trygon
Mon, Nov 16, 2015 3:11 PM

OpenSCAD currently supports a whole range of specific linear transformations
such as translate(), rotate() and scale(), in addition to the generic linear
transformation multmatrix().

OpenSCAD does not provide support for non-linear transformations.  I think
support for non-linear transformations would be very useful and this could
be accomplished with a new transformation command:

transform(x_expression, y_expression, z_expression)

reserved names within transform() expressions: x, y & z, these represent the
vertex being processed

The examples below use this syntax.

Equivalent Linear Transformations:

  1. pass data through, no change to vertices
    transform(x, y, z) { ... }

  2. scale([xf,yf,zf]) { ... }  <->  transform(xfx, yfy, zf*z) { ... }

  3. translate([x1,y1,z1]) { ... }  <->  transform(x+x1, y+y1, z+z1) { ... }

  4. multmatrix([[xx, xy, xz, xc], [yx, yy, yz, yc], [zx, zy, zz, zc], [0, 0,
    0, 1]) { ... }  <->
    transform(xxx+xyy+xzz+xc, yxx+yyy+yzz+yc, zxx+zyy+zz*z+zc) { ...
    }

Non-Linear Transformations:

  1. exponential x scaling
    transform(x*x, y, z) { ... }

  2. "conic" expansion in x-y plane, scale factor=1 for z=20
    transform(xz/20 ,yz/20 ,z) cylinder(h=40, r=10);

  3. scale specific co-ordinate ranges
    transform(x>0?2x:x, abs(y)>50?3y:y, z) { ... }

  4. insert "gap" of 40mm centred on y=0
    transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10);

Comments please!

Cheers,
Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

OpenSCAD currently supports a whole range of specific linear transformations such as translate(), rotate() and scale(), in addition to the generic linear transformation multmatrix(). OpenSCAD does not provide support for non-linear transformations. I think support for non-linear transformations would be very useful and this could be accomplished with a new transformation command: transform(x_expression, y_expression, z_expression) reserved names within transform() expressions: x, y & z, these represent the vertex being processed The examples below use this syntax. Equivalent Linear Transformations: 1) pass data through, no change to vertices transform(x, y, z) { ... } 2) scale([xf,yf,zf]) { ... } <-> transform(xf*x, yf*y, zf*z) { ... } 3) translate([x1,y1,z1]) { ... } <-> transform(x+x1, y+y1, z+z1) { ... } 4) multmatrix([[xx, xy, xz, xc], [yx, yy, yz, yc], [zx, zy, zz, zc], [0, 0, 0, 1]) { ... } <-> transform(xx*x+xy*y+xz*z+xc, yx*x+yy*y+yz*z+yc, zx*x+zy*y+zz*z+zc) { ... } Non-Linear Transformations: 1) exponential x scaling transform(x*x, y, z) { ... } 2) "conic" expansion in x-y plane, scale factor=1 for z=20 transform(x*z/20 ,y*z/20 ,z) cylinder(h=40, r=10); 3) scale specific co-ordinate ranges transform(x>0?2*x:x, abs(y)>50?3*y:y, z) { ... } 4) insert "gap" of 40mm centred on y=0 transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10); Comments please! Cheers, Trygon -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539.html Sent from the OpenSCAD mailing list archive at Nabble.com.
MK
Marius Kintel
Mon, Nov 16, 2015 3:29 PM

On Nov 16, 2015, at 10:11 AM, Trygon db5765@outlook.com wrote:

OpenSCAD does not provide support for non-linear transformations.  I think
support for non-linear transformations would be very useful and this could
be accomplished with a new transformation command:

Would this be conceptually similar to the proposed bend modifier?

https://github.com/openscad/openscad/issues/815

-Marius

> On Nov 16, 2015, at 10:11 AM, Trygon <db5765@outlook.com> wrote: > > OpenSCAD does not provide support for non-linear transformations. I think > support for non-linear transformations would be very useful and this could > be accomplished with a new transformation command: > Would this be conceptually similar to the proposed bend modifier? https://github.com/openscad/openscad/issues/815 -Marius
DM
doug moen
Mon, Nov 16, 2015 3:36 PM

This is a good example of what OpenSCAD2 is designed to enable.

OpenSCAD2 supports functions as first class values: functions can be passed
as arguments and returned as results. So the 'transform' module would not
need to be implemented as magic syntax. It would just be an ordinary module
that is passed 3 functions as arguments.

The syntax would look something like this:

// "conic" expansion in x-y plane, scale factor=1 for z=20
transform(fx(x)=xz/20, fy(y)=yz/20, fz(z)=z) cylinder(h=40, r=10);

The identity function gets used a lot with your scheme, so maybe we
predefine it. This is OpenSCAD2 function definition syntax:

id(x) = x;

Then,
// exponential x scaling
transform(fx(x)=x*x, fy=id, fz=id) { ... }

or just
transform(fx(x)=x*x, id, id) { ... }

On 16 November 2015 at 10:11, Trygon db5765@outlook.com wrote:

OpenSCAD currently supports a whole range of specific linear
transformations
such as translate(), rotate() and scale(), in addition to the generic
linear
transformation multmatrix().

OpenSCAD does not provide support for non-linear transformations.  I think
support for non-linear transformations would be very useful and this could
be accomplished with a new transformation command:

transform(x_expression, y_expression, z_expression)

reserved names within transform() expressions: x, y & z, these represent
the
vertex being processed

The examples below use this syntax.

Equivalent Linear Transformations:

  1. pass data through, no change to vertices
    transform(x, y, z) { ... }

  2. scale([xf,yf,zf]) { ... }  <->  transform(xfx, yfy, zf*z) { ... }

  3. translate([x1,y1,z1]) { ... }  <->  transform(x+x1, y+y1, z+z1) { ...
    }

  4. multmatrix([[xx, xy, xz, xc], [yx, yy, yz, yc], [zx, zy, zz, zc], [0, 0,
    0, 1]) { ... }  <->
    transform(xxx+xyy+xzz+xc, yxx+yyy+yzz+yc, zxx+zyy+zz*z+zc) {
    ...
    }

Non-Linear Transformations:

  1. exponential x scaling
    transform(x*x, y, z) { ... }

  2. "conic" expansion in x-y plane, scale factor=1 for z=20
    transform(xz/20 ,yz/20 ,z) cylinder(h=40, r=10);

  3. scale specific co-ordinate ranges
    transform(x>0?2x:x, abs(y)>50?3y:y, z) { ... }

  4. insert "gap" of 40mm centred on y=0
    transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10);

Comments please!

Cheers,
Trygon

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

This is a good example of what OpenSCAD2 is designed to enable. OpenSCAD2 supports functions as first class values: functions can be passed as arguments and returned as results. So the 'transform' module would not need to be implemented as magic syntax. It would just be an ordinary module that is passed 3 functions as arguments. The syntax would look something like this: // "conic" expansion in x-y plane, scale factor=1 for z=20 transform(fx(x)=x*z/20, fy(y)=y*z/20, fz(z)=z) cylinder(h=40, r=10); The identity function gets used a lot with your scheme, so maybe we predefine it. This is OpenSCAD2 function definition syntax: id(x) = x; Then, // exponential x scaling transform(fx(x)=x*x, fy=id, fz=id) { ... } or just transform(fx(x)=x*x, id, id) { ... } On 16 November 2015 at 10:11, Trygon <db5765@outlook.com> wrote: > OpenSCAD currently supports a whole range of specific linear > transformations > such as translate(), rotate() and scale(), in addition to the generic > linear > transformation multmatrix(). > > OpenSCAD does not provide support for non-linear transformations. I think > support for non-linear transformations would be very useful and this could > be accomplished with a new transformation command: > > transform(x_expression, y_expression, z_expression) > > reserved names within transform() expressions: x, y & z, these represent > the > vertex being processed > > The examples below use this syntax. > > Equivalent Linear Transformations: > > 1) pass data through, no change to vertices > transform(x, y, z) { ... } > > 2) scale([xf,yf,zf]) { ... } <-> transform(xf*x, yf*y, zf*z) { ... } > > 3) translate([x1,y1,z1]) { ... } <-> transform(x+x1, y+y1, z+z1) { ... > } > > 4) multmatrix([[xx, xy, xz, xc], [yx, yy, yz, yc], [zx, zy, zz, zc], [0, 0, > 0, 1]) { ... } <-> > transform(xx*x+xy*y+xz*z+xc, yx*x+yy*y+yz*z+yc, zx*x+zy*y+zz*z+zc) { > ... > } > > Non-Linear Transformations: > > 1) exponential x scaling > transform(x*x, y, z) { ... } > > 2) "conic" expansion in x-y plane, scale factor=1 for z=20 > transform(x*z/20 ,y*z/20 ,z) cylinder(h=40, r=10); > > 3) scale specific co-ordinate ranges > transform(x>0?2*x:x, abs(y)>50?3*y:y, z) { ... } > > 4) insert "gap" of 40mm centred on y=0 > transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10); > > Comments please! > > Cheers, > Trygon > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
MH
Martin Herdieckerhoff
Mon, Nov 16, 2015 3:36 PM

I like the idea of providing non-linear transformations.
However, the suggested approach seems to break the current treatment of
parameters.
The suggested syntax looks as if conventional parameters were passed,
but actually the arguments need to be treated in a very different way,
that is as functions.
Others will know better if that syntax fits into the language.
But I am afraid that it does not.
What about enhancing the language by functions as arguments to provide
the suggested functionality?
Am 16.11.2015 um 16:11 schrieb Trygon:

OpenSCAD currently supports a whole range of specific linear transformations
such as translate(), rotate() and scale(), in addition to the generic linear
transformation multmatrix().

OpenSCAD does not provide support for non-linear transformations.  I think
support for non-linear transformations would be very useful and this could
be accomplished with a new transformation command:

transform(x_expression, y_expression, z_expression)

reserved names within transform() expressions: x, y & z, these represent the
vertex being processed

The examples below use this syntax.

Equivalent Linear Transformations:

  1. pass data through, no change to vertices
    transform(x, y, z) { ... }

  2. scale([xf,yf,zf]) { ... }  <->  transform(xfx, yfy, zf*z) { ... }

  3. translate([x1,y1,z1]) { ... }  <->  transform(x+x1, y+y1, z+z1) { ... }

  4. multmatrix([[xx, xy, xz, xc], [yx, yy, yz, yc], [zx, zy, zz, zc], [0, 0,
    0, 1]) { ... }  <->
    transform(xxx+xyy+xzz+xc, yxx+yyy+yzz+yc, zxx+zyy+zz*z+zc) { ...
    }

Non-Linear Transformations:

  1. exponential x scaling
    transform(x*x, y, z) { ... }

  2. "conic" expansion in x-y plane, scale factor=1 for z=20
    transform(xz/20 ,yz/20 ,z) cylinder(h=40, r=10);

  3. scale specific co-ordinate ranges
    transform(x>0?2x:x, abs(y)>50?3y:y, z) { ... }

  4. insert "gap" of 40mm centred on y=0
    transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10);

Comments please!

Cheers,
Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

**

I like the idea of providing non-linear transformations. However, the suggested approach seems to break the current treatment of parameters. The suggested syntax looks as if conventional parameters were passed, but actually the arguments need to be treated in a very different way, that is as functions. Others will know better if that syntax fits into the language. But I am afraid that it does not. What about enhancing the language by functions as arguments to provide the suggested functionality? Am 16.11.2015 um 16:11 schrieb Trygon: > OpenSCAD currently supports a whole range of specific linear transformations > such as translate(), rotate() and scale(), in addition to the generic linear > transformation multmatrix(). > > OpenSCAD does not provide support for non-linear transformations. I think > support for non-linear transformations would be very useful and this could > be accomplished with a new transformation command: > > transform(x_expression, y_expression, z_expression) > > reserved names within transform() expressions: x, y & z, these represent the > vertex being processed > > The examples below use this syntax. > > Equivalent Linear Transformations: > > 1) pass data through, no change to vertices > transform(x, y, z) { ... } > > 2) scale([xf,yf,zf]) { ... } <-> transform(xf*x, yf*y, zf*z) { ... } > > 3) translate([x1,y1,z1]) { ... } <-> transform(x+x1, y+y1, z+z1) { ... } > > 4) multmatrix([[xx, xy, xz, xc], [yx, yy, yz, yc], [zx, zy, zz, zc], [0, 0, > 0, 1]) { ... } <-> > transform(xx*x+xy*y+xz*z+xc, yx*x+yy*y+yz*z+yc, zx*x+zy*y+zz*z+zc) { ... > } > > Non-Linear Transformations: > > 1) exponential x scaling > transform(x*x, y, z) { ... } > > 2) "conic" expansion in x-y plane, scale factor=1 for z=20 > transform(x*z/20 ,y*z/20 ,z) cylinder(h=40, r=10); > > 3) scale specific co-ordinate ranges > transform(x>0?2*x:x, abs(y)>50?3*y:y, z) { ... } > > 4) insert "gap" of 40mm centred on y=0 > transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10); > > Comments please! > > Cheers, > Trygon > > > > > -- > View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > **
C
ctchin
Mon, Nov 16, 2015 5:35 PM

Trygon wrote

  1. exponential x scaling
    transform(x*x, y, z) { ... }

  2. "conic" expansion in x-y plane, scale factor=1 for z=20
    transform(xz/20 ,yz/20 ,z) cylinder(h=40, r=10);

  3. scale specific co-ordinate ranges
    transform(x>0?2x:x, abs(y)>50?3y:y, z) { ... }

  4. insert "gap" of 40mm centred on y=0
    transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10);

  1. exponential: it should better be called power law or polynomial.
    It's a relatively unique requirement...

  2. conic: I believe it's actually linear and doable with a
    simple multmatrix()

  3. scale specific co-ordinate ranges and 4) insert gap
    both are easily doable with a smartly written module
    using difference() and/or projection()

So only the x = x*x exponential (sic) is new, I'm not
very convinced it justifies inventing a whole new syntax
for it.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14548.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Trygon wrote > 1) exponential x scaling > transform(x*x, y, z) { ... } > > 2) "conic" expansion in x-y plane, scale factor=1 for z=20 > transform(x*z/20 ,y*z/20 ,z) cylinder(h=40, r=10); > > 3) scale specific co-ordinate ranges > transform(x>0?2*x:x, abs(y)>50?3*y:y, z) { ... } > > 4) insert "gap" of 40mm centred on y=0 > transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10); 1) exponential: it should better be called power law or polynomial. It's a relatively unique requirement... 2) conic: I believe it's actually linear and doable with a simple multmatrix() 3) scale specific co-ordinate ranges and 4) insert gap both are easily doable with a smartly written module using difference() and/or projection() So only the x = x*x exponential (sic) is new, I'm not very convinced it justifies inventing a whole new syntax for it. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14548.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Mon, Nov 16, 2015 6:02 PM

Another way to represent the transformation is as a single function that
maps a point [x,y,z] to another point.

If you think of this function as mapping every point in a 3D shape, then
this is extremely powerful, as you can model any conceivable spatial
transformation: twisting, bending, etc.

In practice, there are difficulties, as pointed out by
https://github.com/openscad/openscad/issues/815

The problem is that, with many of the more interesting transformations,
it's not enough to simply transform each vertex. You may need to subdivide
the mesh to create smaller faces, and then transform each vertex in the
subdivided mesh. An example would be applying a twist or bend
transformation to a cube, with just the 8 vertices.

On 16 November 2015 at 12:35, ctchin c.t.chin@szu.edu.cn wrote:

Trygon wrote

  1. exponential x scaling
    transform(x*x, y, z) { ... }

  2. "conic" expansion in x-y plane, scale factor=1 for z=20
    transform(xz/20 ,yz/20 ,z) cylinder(h=40, r=10);

  3. scale specific co-ordinate ranges
    transform(x>0?2x:x, abs(y)>50?3y:y, z) { ... }

  4. insert "gap" of 40mm centred on y=0
    transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10);

  1. exponential: it should better be called power law or polynomial.
    It's a relatively unique requirement...

  2. conic: I believe it's actually linear and doable with a
    simple multmatrix()

  3. scale specific co-ordinate ranges and 4) insert gap
    both are easily doable with a smartly written module
    using difference() and/or projection()

So only the x = x*x exponential (sic) is new, I'm not
very convinced it justifies inventing a whole new syntax
for it.

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14548.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

Another way to represent the transformation is as a single function that maps a point [x,y,z] to another point. If you think of this function as mapping every point in a 3D shape, then this is extremely powerful, as you can model any conceivable spatial transformation: twisting, bending, etc. In practice, there are difficulties, as pointed out by https://github.com/openscad/openscad/issues/815 The problem is that, with many of the more interesting transformations, it's not enough to simply transform each vertex. You may need to subdivide the mesh to create smaller faces, and then transform each vertex in the subdivided mesh. An example would be applying a twist or bend transformation to a cube, with just the 8 vertices. On 16 November 2015 at 12:35, ctchin <c.t.chin@szu.edu.cn> wrote: > Trygon wrote > > 1) exponential x scaling > > transform(x*x, y, z) { ... } > > > > 2) "conic" expansion in x-y plane, scale factor=1 for z=20 > > transform(x*z/20 ,y*z/20 ,z) cylinder(h=40, r=10); > > > > 3) scale specific co-ordinate ranges > > transform(x>0?2*x:x, abs(y)>50?3*y:y, z) { ... } > > > > 4) insert "gap" of 40mm centred on y=0 > > transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10); > > 1) exponential: it should better be called power law or polynomial. > It's a relatively unique requirement... > > 2) conic: I believe it's actually linear and doable with a > simple multmatrix() > > 3) scale specific co-ordinate ranges and 4) insert gap > both are easily doable with a smartly written module > using difference() and/or projection() > > So only the x = x*x exponential (sic) is new, I'm not > very convinced it justifies inventing a whole new syntax > for it. > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14548.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org >
T
Trygon
Mon, Nov 16, 2015 6:09 PM

Yes this could be used to bend objects, I think this would work:

transform(ysin(x), ycos(x), z)

As noted in the proposed bend modifier discussion, unless the object has
sufficient vertices it will just deform (unpleasantly), e.g. a simple cube
with 8 vertices would not work well. However this is a different issue.

If the use of x, y & z as reserved names makes the "syntax looks as if
conventional parameters were passed", perhaps x(), y() & z() could be used
instead as reserved functions, such that "the arguments need to
be...functions"?

The above example would become:

transform( y()*sin(x()), y()*cos(x()), z() )

-Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14551.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Yes this could be used to bend objects, I think this would work: transform(y*sin(x), y*cos(x), z) As noted in the proposed bend modifier discussion, unless the object has sufficient vertices it will just deform (unpleasantly), e.g. a simple cube with 8 vertices would not work well. However this is a different issue. If the use of x, y & z as reserved names makes the "syntax looks as if conventional parameters were passed", perhaps x(), y() & z() could be used instead as reserved functions, such that "the arguments need to be...functions"? The above example would become: transform( y()*sin(x()), y()*cos(x()), z() ) -Trygon -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14551.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Mon, Nov 16, 2015 6:13 PM

Following up on the "subdivision problem".

I really like the proposal from Trygon last month of using a $fe variable
to specify the "maximal acceptable error" in a polygonal approximation of a
solid.

Having come to OpenSCAD primarily from a design engineering background I am
used to specifying tolerances for specific features, e.g. 20mm +/- 0.1mm.
Wanting to use this principle for arc approximation I have adopted the
approach set out below which I hope might be useful to others.

The maximum error for a facet occurs at it centre, when it is furthest from
the true circular arc that it approximates. I use variable $fe in my
OpenSCAD scripts to specify the maximum acceptable value of this error (the
distance from the centre of the facet to the true circular arc, measured
normal to the facet).  I then use the following function to calculate a
value for $fa based on the arc radius and $fe:

So now I'm wondering if we can create an algorithm for optimally
subdividing a polygon, using the minimum number of subdivisions necessary
to keep the error below $fe, when applying one of Trygon's generalized
spatial tranformations. I think it makes sense. We transform all of the
vertexes in a face, then we perform a trial subdivision of that face,
transform the added vertexes, and measure if the added vertexes were
necessary.

On 16 November 2015 at 13:02, doug moen doug@moens.org wrote:

Another way to represent the transformation is as a single function that
maps a point [x,y,z] to another point.

If you think of this function as mapping every point in a 3D shape, then
this is extremely powerful, as you can model any conceivable spatial
transformation: twisting, bending, etc.

In practice, there are difficulties, as pointed out by
https://github.com/openscad/openscad/issues/815

The problem is that, with many of the more interesting transformations,
it's not enough to simply transform each vertex. You may need to subdivide
the mesh to create smaller faces, and then transform each vertex in the
subdivided mesh. An example would be applying a twist or bend
transformation to a cube, with just the 8 vertices.

On 16 November 2015 at 12:35, ctchin c.t.chin@szu.edu.cn wrote:

Trygon wrote

  1. exponential x scaling
    transform(x*x, y, z) { ... }

  2. "conic" expansion in x-y plane, scale factor=1 for z=20
    transform(xz/20 ,yz/20 ,z) cylinder(h=40, r=10);

  3. scale specific co-ordinate ranges
    transform(x>0?2x:x, abs(y)>50?3y:y, z) { ... }

  4. insert "gap" of 40mm centred on y=0
    transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10);

  1. exponential: it should better be called power law or polynomial.
    It's a relatively unique requirement...

  2. conic: I believe it's actually linear and doable with a
    simple multmatrix()

  3. scale specific co-ordinate ranges and 4) insert gap
    both are easily doable with a smartly written module
    using difference() and/or projection()

So only the x = x*x exponential (sic) is new, I'm not
very convinced it justifies inventing a whole new syntax
for it.

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14548.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

Following up on the "subdivision problem". I really like the proposal from Trygon last month of using a $fe variable to specify the "maximal acceptable error" in a polygonal approximation of a solid. Having come to OpenSCAD primarily from a design engineering background I am used to specifying tolerances for specific features, e.g. 20mm +/- 0.1mm. Wanting to use this principle for arc approximation I have adopted the approach set out below which I hope might be useful to others. The maximum error for a facet occurs at it centre, when it is furthest from the true circular arc that it approximates. I use variable $fe in my OpenSCAD scripts to specify the maximum acceptable value of this error (the distance from the centre of the facet to the true circular arc, measured normal to the facet). I then use the following function to calculate a value for $fa based on the arc radius and $fe: So now I'm wondering if we can create an algorithm for optimally subdividing a polygon, using the minimum number of subdivisions necessary to keep the error below $fe, when applying one of Trygon's generalized spatial tranformations. I think it makes sense. We transform all of the vertexes in a face, then we perform a trial subdivision of that face, transform the added vertexes, and measure if the added vertexes were necessary. On 16 November 2015 at 13:02, doug moen <doug@moens.org> wrote: > Another way to represent the transformation is as a single function that > maps a point [x,y,z] to another point. > > If you think of this function as mapping every point in a 3D shape, then > this is extremely powerful, as you can model any conceivable spatial > transformation: twisting, bending, etc. > > In practice, there are difficulties, as pointed out by > https://github.com/openscad/openscad/issues/815 > > The problem is that, with many of the more interesting transformations, > it's not enough to simply transform each vertex. You may need to subdivide > the mesh to create smaller faces, and then transform each vertex in the > subdivided mesh. An example would be applying a twist or bend > transformation to a cube, with just the 8 vertices. > > On 16 November 2015 at 12:35, ctchin <c.t.chin@szu.edu.cn> wrote: > >> Trygon wrote >> > 1) exponential x scaling >> > transform(x*x, y, z) { ... } >> > >> > 2) "conic" expansion in x-y plane, scale factor=1 for z=20 >> > transform(x*z/20 ,y*z/20 ,z) cylinder(h=40, r=10); >> > >> > 3) scale specific co-ordinate ranges >> > transform(x>0?2*x:x, abs(y)>50?3*y:y, z) { ... } >> > >> > 4) insert "gap" of 40mm centred on y=0 >> > transform(x ,y>0?y+20:y-20, z) cylinder(h=20, r=10); >> >> 1) exponential: it should better be called power law or polynomial. >> It's a relatively unique requirement... >> >> 2) conic: I believe it's actually linear and doable with a >> simple multmatrix() >> >> 3) scale specific co-ordinate ranges and 4) insert gap >> both are easily doable with a smartly written module >> using difference() and/or projection() >> >> So only the x = x*x exponential (sic) is new, I'm not >> very convinced it justifies inventing a whole new syntax >> for it. >> >> >> >> >> -- >> View this message in context: >> http://forum.openscad.org/Non-Linear-Transformations-tp14539p14548.html >> Sent from the OpenSCAD mailing list archive at Nabble.com. >> >> _______________________________________________ >> OpenSCAD mailing list >> Discuss@lists.openscad.org >> http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org >> > >
C
ctchin
Mon, Nov 16, 2015 6:35 PM

The more I read the more I understand the request, the more
I'm convinced there's a lot loony ideas being thrown around.

The syntax x(), whether it's built-in or not, is a function call
with no input parameters (adopting the default values if possible).

For non-linear or more precisely non-affine transformation to
work the way you imagine it, will require re-meshing the children
with some level of smartly selected resolution.  Which spells...
no universally acceptable algorithm exists.

If it doesn't work sensibly on a cube() primitive, it's highly
questionable it ought to be added to OpenSCAD.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14553.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

The more I read the more I understand the request, the more I'm convinced there's a lot loony ideas being thrown around. The syntax x(), whether it's built-in or not, is a function call with no input parameters (adopting the default values if possible). For non-linear or more precisely non-affine transformation to work the way you imagine it, will require re-meshing the children with some level of smartly selected resolution. Which spells... no universally acceptable algorithm exists. If it doesn't work sensibly on a cube() primitive, it's highly questionable it ought to be added to OpenSCAD. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14553.html Sent from the OpenSCAD mailing list archive at Nabble.com.
T
Trygon
Mon, Nov 16, 2015 6:36 PM

// non-linear transformation: 2D bend demo

x1=-40;
x2=40;
y1=30;
y2=40;
step=10;

p1=concat([for(i=[x1:step:x2]) [i,y1]],[for(i=[x2:-step:x1]) [i,y2]]);
polygon(p1);

// translate([0,-20,0]) transform(ysin(x),ycos(x)) polygon(p1);
p2=[for(i=p1) [i[1]*sin(i[0]),i[1]*cos(i[0])]];
translate ([0,-20,0]) polygon(p2);

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14554.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

// non-linear transformation: 2D bend demo x1=-40; x2=40; y1=30; y2=40; step=10; p1=concat([for(i=[x1:step:x2]) [i,y1]],[for(i=[x2:-step:x1]) [i,y2]]); polygon(p1); // translate([0,-20,0]) transform(y*sin(x),y*cos(x)) polygon(p1); p2=[for(i=p1) [i[1]*sin(i[0]),i[1]*cos(i[0])]]; translate ([0,-20,0]) polygon(p2); -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14554.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Mon, Nov 16, 2015 6:50 PM

ctchin said:

For non-linear or more precisely non-affine transformation to
work the way you imagine it, will require re-meshing the children
with some level of smartly selected resolution.  Which spells...
no universally acceptable algorithm exists.

I just described (in a vague way) a smart re-meshing algorithm in a
previous post. I'd like to hear why my algorithm might not be acceptable.

Here it is again, in more detail. Let's assume the polyhedron mesh is made
of triangles. For each triangle, we transform the vertexes. Then, we
perform a trial subdivision of the triangle into 4 smaller triangles, by
bisecting each of the original edges. This adds 3 new vertexes. We
transform each vertex, and compute the height of the vertex above the
parent triangle, in the direction of the parent triangle's normal vector. A
height of 0 means the new vertex lies in the plane of the parent triangle.
If all of the 3 new vertexes have a height of < $fe, then we discard the
new vertexes. Otherwise, we keep the new vertexes, and iterate, subdividing
the newly created triangles.

Doug.

On 16 November 2015 at 13:35, ctchin c.t.chin@szu.edu.cn wrote:

The more I read the more I understand the request, the more
I'm convinced there's a lot loony ideas being thrown around.

The syntax x(), whether it's built-in or not, is a function call
with no input parameters (adopting the default values if possible).

For non-linear or more precisely non-affine transformation to
work the way you imagine it, will require re-meshing the children
with some level of smartly selected resolution.  Which spells...
no universally acceptable algorithm exists.

If it doesn't work sensibly on a cube() primitive, it's highly
questionable it ought to be added to OpenSCAD.

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14553.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

ctchin said: > For non-linear or more precisely non-affine transformation to > work the way you imagine it, will require re-meshing the children > with some level of smartly selected resolution. Which spells... > no universally acceptable algorithm exists. I just described (in a vague way) a smart re-meshing algorithm in a previous post. I'd like to hear why my algorithm might not be acceptable. Here it is again, in more detail. Let's assume the polyhedron mesh is made of triangles. For each triangle, we transform the vertexes. Then, we perform a trial subdivision of the triangle into 4 smaller triangles, by bisecting each of the original edges. This adds 3 new vertexes. We transform each vertex, and compute the height of the vertex above the parent triangle, in the direction of the parent triangle's normal vector. A height of 0 means the new vertex lies in the plane of the parent triangle. If all of the 3 new vertexes have a height of < $fe, then we discard the new vertexes. Otherwise, we keep the new vertexes, and iterate, subdividing the newly created triangles. Doug. On 16 November 2015 at 13:35, ctchin <c.t.chin@szu.edu.cn> wrote: > The more I read the more I understand the request, the more > I'm convinced there's a lot loony ideas being thrown around. > > The syntax x(), whether it's built-in or not, is a function call > with no input parameters (adopting the default values if possible). > > For non-linear or more precisely non-affine transformation to > work the way you imagine it, will require re-meshing the children > with some level of smartly selected resolution. Which spells... > no universally acceptable algorithm exists. > > If it doesn't work sensibly on a cube() primitive, it's highly > questionable it ought to be added to OpenSCAD. > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14553.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
P
Parkinbot
Mon, Nov 16, 2015 7:27 PM

You are perfectly right!

Anyway only ismorphic nonlinear transformations would make sense. Most of
them are not isomorphic in a general sense - but might be in a subset, as
the given examples.

A more general approach for this feature would be to get hands on the mesh
points, as requested in my topic "feature request: obj2vec(); bug report:
freeze on standby recovery (Windows)". Then, everyone is free to use his own
mappings even non-isomorphic ones and also responsible if the resulting
polyhedron will be malformed.

If it doesn't work sensibly on a cube() primitive, it's highly
questionable it ought to be added to OpenSCAD.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14565.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

You are perfectly right! Anyway only ismorphic nonlinear transformations would make sense. Most of them are not isomorphic in a general sense - but might be in a subset, as the given examples. A more general approach for this feature would be to get hands on the mesh points, as requested in my topic "feature request: obj2vec(); bug report: freeze on standby recovery (Windows)". Then, everyone is free to use his own mappings even non-isomorphic ones and also responsible if the resulting polyhedron will be malformed. > If it doesn't work sensibly on a cube() primitive, it's highly > questionable it ought to be added to OpenSCAD. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14565.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Mon, Nov 16, 2015 7:58 PM

Parkinbot, could you explain your comment "Anyway only ismorphic nonlinear
transformations would make sense."  What will go wrong if a non-isomorphic
transformation is specified?

Isomorphic means that the structure of the geometric object is preserved,
in the sense that there is a reverse transformation that takes the
transformed object back to the original.

I can imagine evil transformations that result in a non-manifold object, or
which cause my smart-remeshing algorithm to go into an infinite loop. I
think we'd want error checking to detect these situations and report an
error.

I'm not sure how to prove that all non-isomorphic transformations are evil.
My math is not as strong as some of the other people on this list. But you
seem to know this as a fact, so how do you know?

On 16 November 2015 at 14:27, Parkinbot rudolf@parkinbot.com wrote:

You are perfectly right!

Anyway only ismorphic nonlinear transformations would make sense. Most of
them are not isomorphic in a general sense - but might be in a subset, as
the given examples.

A more general approach for this feature would be to get hands on the mesh
points, as requested in my topic "feature request: obj2vec(); bug report:
freeze on standby recovery (Windows)". Then, everyone is free to use his
own
mappings even non-isomorphic ones and also responsible if the resulting
polyhedron will be malformed.

If it doesn't work sensibly on a cube() primitive, it's highly
questionable it ought to be added to OpenSCAD.

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14565.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

Parkinbot, could you explain your comment "Anyway only ismorphic nonlinear transformations would make sense." What will go wrong if a non-isomorphic transformation is specified? Isomorphic means that the structure of the geometric object is preserved, in the sense that there is a reverse transformation that takes the transformed object back to the original. I can imagine evil transformations that result in a non-manifold object, or which cause my smart-remeshing algorithm to go into an infinite loop. I think we'd want error checking to detect these situations and report an error. I'm not sure how to prove that all non-isomorphic transformations are evil. My math is not as strong as some of the other people on this list. But you seem to know this as a fact, so how do you know? On 16 November 2015 at 14:27, Parkinbot <rudolf@parkinbot.com> wrote: > You are perfectly right! > > Anyway only ismorphic nonlinear transformations would make sense. Most of > them are not isomorphic in a general sense - but might be in a subset, as > the given examples. > > A more general approach for this feature would be to get hands on the mesh > points, as requested in my topic "feature request: obj2vec(); bug report: > freeze on standby recovery (Windows)". Then, everyone is free to use his > own > mappings even non-isomorphic ones and also responsible if the resulting > polyhedron will be malformed. > > > If it doesn't work sensibly on a cube() primitive, it's highly > > questionable it ought to be added to OpenSCAD. > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14565.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
P
Parkinbot
Mon, Nov 16, 2015 9:18 PM

Well, a non-isomorphic map in R³->R³ will have singularities (points, lines
or planes) in the sense that more than one points will be mapped to the same
point - so no inverse map can be found. As bijectivity is lost, vertices and
triangles simply might get lost.
Restricting a non-isomorphic map to a region (partial isomorphism), say to
the unit cube, it might be locally isomorphic as long as the region does not
contain any fix points.
So if we have a (partial) isomorphism all points (of a region) will be
mapped to separate image points and no merging can occur (numerically yes,
which is still another severe problem). Also triangle orientation will be
mapped in the same sense, as a partial flip of orientation of a triangle
would need a singularity for separation.

But you are right. Proving that a map is a (partial) isomorphism will only
be a first step. Even then, non-intersecting triangles might intersect after
being mapped (think of simply mapping one axis to a vortex like the
Archimedian spiral), and demand some careful post processing.

To sum it up: Non-linear operations have many pitfalls.

I guess one could allow for some of them in very specific contexts, like
with extrusion operations. For linear_extrusion() instead of linear scaling
and twisting one could think of nonlinear stepping or allow for a vector
expressing an ordered list of values, which will be used as z-heights, while
scaling and twisting will be done in a linear fashion with equidistant
stepping as it is done now.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14578.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Well, a non-isomorphic map in R³->R³ will have singularities (points, lines or planes) in the sense that more than one points will be mapped to the same point - so no inverse map can be found. As bijectivity is lost, vertices and triangles simply might get lost. Restricting a non-isomorphic map to a region (partial isomorphism), say to the unit cube, it might be locally isomorphic as long as the region does not contain any fix points. So if we have a (partial) isomorphism all points (of a region) will be mapped to separate image points and no merging can occur (numerically yes, which is still another severe problem). Also triangle orientation will be mapped in the same sense, as a partial flip of orientation of a triangle would need a singularity for separation. But you are right. Proving that a map is a (partial) isomorphism will only be a first step. Even then, non-intersecting triangles might intersect after being mapped (think of simply mapping one axis to a vortex like the Archimedian spiral), and demand some careful post processing. To sum it up: Non-linear operations have many pitfalls. I guess one could allow for some of them in very specific contexts, like with extrusion operations. For linear_extrusion() instead of linear scaling and twisting one could think of nonlinear stepping or allow for a vector expressing an ordered list of values, which will be used as z-heights, while scaling and twisting will be done in a linear fashion with equidistant stepping as it is done now. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14578.html Sent from the OpenSCAD mailing list archive at Nabble.com.
T
Trygon
Mon, Nov 16, 2015 9:37 PM

@ctchin you said, "conic: I believe it's actually linear and doable with a
simple multmatrix()", with regard to:

transform(xz/20 ,yz/20 ,z)

This transformation would be really useful for a model that I am scripting
at present, I couldn't work out how to do it with multmatrix(), please could
you provide the affine transformation matrix to use.

Thanks,
Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14579.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

@ctchin you said, "conic: I believe it's actually linear and doable with a simple multmatrix()", with regard to: transform(x*z/20 ,y*z/20 ,z) This transformation would be really useful for a model that I am scripting at present, I couldn't work out how to do it with multmatrix(), please could you provide the affine transformation matrix to use. Thanks, Trygon -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14579.html Sent from the OpenSCAD mailing list archive at Nabble.com.
N
Neon22
Mon, Nov 16, 2015 9:45 PM

@Doug - This remeshing algorithm was designed specifically for this exact
purpose and worked very well at the time. (1992). May be worth a read:

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14581.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

@Doug - This remeshing algorithm was designed specifically for this exact purpose and worked very well at the time. (1992). May be worth a read: - http://www.red3d.com/cwr/papers/1992/df.html -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14581.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Mon, Nov 16, 2015 9:52 PM

Hi Trygon. Wikipedia uses the term "perspective transformation" for what
you call a conic transformation.

I tried using the perspective transformation matrix from wikipedia in
OpenSCAD and it didn't work, I got a run-time error. Don't remember the
details, it was a while ago. At the time, I concluded that we don't support
arbitrary affine transformations.

If someone has working code, I'd like to see it.

On 16 November 2015 at 16:37, Trygon db5765@outlook.com wrote:

@ctchin you said, "conic: I believe it's actually linear and doable with a
simple multmatrix()", with regard to:

transform(xz/20 ,yz/20 ,z)

This transformation would be really useful for a model that I am scripting
at present, I couldn't work out how to do it with multmatrix(), please
could
you provide the affine transformation matrix to use.

Thanks,
Trygon

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14579.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

Hi Trygon. Wikipedia uses the term "perspective transformation" for what you call a conic transformation. I tried using the perspective transformation matrix from wikipedia in OpenSCAD and it didn't work, I got a run-time error. Don't remember the details, it was a while ago. At the time, I concluded that we don't support arbitrary affine transformations. If someone has working code, I'd like to see it. On 16 November 2015 at 16:37, Trygon <db5765@outlook.com> wrote: > @ctchin you said, "conic: I believe it's actually linear and doable with a > simple multmatrix()", with regard to: > > transform(x*z/20 ,y*z/20 ,z) > > This transformation would be really useful for a model that I am scripting > at present, I couldn't work out how to do it with multmatrix(), please > could > you provide the affine transformation matrix to use. > > Thanks, > Trygon > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14579.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
DM
doug moen
Mon, Nov 16, 2015 9:56 PM

Oh, nice. This algorithm "removes excess detail in crowded regions where
the surface is contracting", which is more sophisticated than what I
specified.

On 16 November 2015 at 16:45, Neon22 mschafer@wireframe.biz wrote:

@Doug - This remeshing algorithm was designed specifically for this exact
purpose and worked very well at the time. (1992). May be worth a read:

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14581.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

Oh, nice. This algorithm "removes excess detail in crowded regions where the surface is contracting", which is more sophisticated than what I specified. On 16 November 2015 at 16:45, Neon22 <mschafer@wireframe.biz> wrote: > @Doug - This remeshing algorithm was designed specifically for this exact > purpose and worked very well at the time. (1992). May be worth a read: > - http://www.red3d.com/cwr/papers/1992/df.html > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14581.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
MK
Marius Kintel
Mon, Nov 16, 2015 10:13 PM

On Nov 16, 2015, at 16:52 PM, doug moen doug@moens.org wrote:

I tried using the perspective transformation matrix from wikipedia in OpenSCAD and it didn't work, I got a run-time error. Don't remember the details, it was a while ago. At the time, I concluded that we don't support arbitrary affine transformations.

The perspective transformation is not affine. We currently don’t support non-affine transformations because CGAL doesn’t.

-Marius

> On Nov 16, 2015, at 16:52 PM, doug moen <doug@moens.org> wrote: > > I tried using the perspective transformation matrix from wikipedia in OpenSCAD and it didn't work, I got a run-time error. Don't remember the details, it was a while ago. At the time, I concluded that we don't support arbitrary affine transformations. > The perspective transformation is not affine. We currently don’t support non-affine transformations because CGAL doesn’t. -Marius
T
Trygon
Mon, Nov 16, 2015 10:34 PM
  1. Given that a transform function could be defined in OpenSCAD as:

function transform(v)=let(x=v[0], y=v[1], z=v[2]) [xz/20, yz/20, z];

which maps a single vertex to a new position (as per doug.moen: vector in,
vector out), perhaps a better syntax would be:

transform()=[xz/20, yz/20, z] { ... }

  1. I have been using non affine transformations in my code for a while and
    the world has not ended. Yes they do have to be used with care, but are
    useful. The main issue is that they can only be used at present when all the
    geometry data has been computed directly so that the vertex data is visible.

-Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14585.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

1) Given that a transform function could be defined in OpenSCAD as: function transform(v)=let(x=v[0], y=v[1], z=v[2]) [x*z/20, y*z/20, z]; which maps a single vertex to a new position (as per doug.moen: vector in, vector out), perhaps a better syntax would be: transform()=[x*z/20, y*z/20, z] { ... } 2) I have been using non affine transformations in my code for a while and the world has not ended. Yes they do have to be used with care, but are useful. The main issue is that they can only be used at present when all the geometry data has been computed directly so that the vertex data is visible. -Trygon -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14585.html Sent from the OpenSCAD mailing list archive at Nabble.com.
R
runsun
Mon, Nov 16, 2015 10:37 PM

doug.moen wrote

Hi Trygon. Wikipedia uses the term "perspective transformation" for what
you call a conic transformation.

I tried using the perspective transformation matrix from wikipedia in
OpenSCAD and it didn't work, I got a run-time error. Don't remember the
details, it was a while ago. At the time, I concluded that we don't
support
arbitrary affine transformations.

If someone has working code, I'd like to see it.

What needed is a line-plane intersection function. As shown in the following
fig ( source
http://www.geom.uiuc.edu/docs/reference/CRC-formulas/node16.html  ):

http://forum.openscad.org/file/n14586/img47.gif

Let p = a point on P, q= a point on Q. A projective transformation focusing
on point O can be obtained by calculating the intersection of line pO with
plane Q. This is achievable.


$  Runsun Pan, PhD

$ libs: doctest , faces ( git ), offline doc ( git ),runscad.py( 1 , 2 , git );

$ tips: hash( 1 , 2 ), sweep , var , lerp , animGif

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14586.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

doug.moen wrote > Hi Trygon. Wikipedia uses the term "perspective transformation" for what > you call a conic transformation. > > I tried using the perspective transformation matrix from wikipedia in > OpenSCAD and it didn't work, I got a run-time error. Don't remember the > details, it was a while ago. At the time, I concluded that we don't > support > arbitrary affine transformations. > > If someone has working code, I'd like to see it. What needed is a line-plane intersection function. As shown in the following fig ( source <http://www.geom.uiuc.edu/docs/reference/CRC-formulas/node16.html> ): <http://forum.openscad.org/file/n14586/img47.gif> Let p = a point on P, q= a point on Q. A projective transformation focusing on point O can be obtained by calculating the intersection of line pO with plane Q. This is achievable. ----- $ Runsun Pan, PhD $ libs: doctest , faces ( git ), offline doc ( git ),runscad.py( 1 , 2 , git ); $ tips: hash( 1 , 2 ), sweep , var , lerp , animGif -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14586.html Sent from the OpenSCAD mailing list archive at Nabble.com.
N
Neon22
Tue, Nov 17, 2015 12:16 AM

I applaud the approach of use mathematical equations to define the curve.
However IMHO we also want to easily support the user making the curve
manually. (current list-comprehensions and paths, lofts not quite easy
enough to use IMHO)

E.g.
A 2D polygon (profile) extruded along its (face) normal by D. Then rotated
around its center by Rz degrees.
Loop this N times to get an extruded "twist" of the profile.
E.g.
Same as above but also rotating Rx each increment around the X axis (on edge
of profile shape).
Changing the above into a twisted arch.
E.g
Same as above but starting profile is a square and ending profile is a
pentagon.
Changing the above into a more complex mesh.

So critical aspects are:

  • Derived normal per iteration, so we tell which direction vector to move
    along.
  • Looping construct around the outside for N steps. (for)
  • Local transformation, so rotating around edge of profile has new
    location(globally) but same location(locally) when in middle of the
    sequence.
  • Ideally a way to interpolate an intermediate shape between two shapes with
    different numbers of vertices.
    Either by:
  • sampling the edges intitially and making more intermediate points, then
    moving each vertex in linear interp(say) at each step.
  • AND/OR by auto-triangulation when increasing number of vertices.

These are the aspects I would like to see in OpenSCAD, to make it easy to
make many more complex useful objects in an incremental, rather than math
function, way.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14588.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

I applaud the approach of use mathematical equations to define the curve. However IMHO we also want to easily support the user making the curve manually. (current list-comprehensions and paths, lofts not quite easy enough to use IMHO) E.g. A 2D polygon (profile) extruded along its (face) normal by D. Then rotated around its center by Rz degrees. Loop this N times to get an extruded "twist" of the profile. E.g. Same as above but also rotating Rx each increment around the X axis (on edge of profile shape). Changing the above into a twisted arch. E.g Same as above but starting profile is a square and ending profile is a pentagon. Changing the above into a more complex mesh. So critical aspects are: - Derived normal per iteration, so we tell which direction vector to move along. - Looping construct around the outside for N steps. (for) - Local transformation, so rotating around edge of profile has new location(globally) but same location(locally) when in middle of the sequence. - Ideally a way to interpolate an intermediate shape between two shapes with different numbers of vertices. Either by: - sampling the edges intitially and making more intermediate points, then moving each vertex in linear interp(say) at each step. - AND/OR by auto-triangulation when increasing number of vertices. These are the aspects I would like to see in OpenSCAD, to make it easy to make many more complex useful objects in an incremental, rather than math function, way. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14588.html Sent from the OpenSCAD mailing list archive at Nabble.com.
C
ctchin
Tue, Nov 17, 2015 5:44 AM

kintel spoted my mistake, x*z is non-affine so, sorry I was wrong on that
point.  I was thinking (I forgot the proper term until doug gave it) about
perspective transformation which can be represented by a 4x4 matrix but not
supported in OpenSCAD.

But he also gave an important clue why a lot of this is loony ideas:

kintel wrote

don’t support non-affine transformations because CGAL doesn’t.

So yes, now that I've been better educated I remember at one point needing
perspective transformation desperately and cursing OpenSCAD for not doing it
for me.  But after some attempts, I switch track to trying to solve my
problem by some ways other than transformation.  Of course there's no
general solution to substituting a general perspective transformation with
legal OpenSCAD commands, but I found a way to do exactly what I wanted to
design at the time, printed it, published it and be done with it.

I see OpenSCAD as a toy, a fantastic toy (hope no one takes offense).  But
it's not a proper programming language.  If my design involves some complex
math or algorithm, I would rather do the math in a language I normally use
for math and engineering problems.  I have written a ton of codes in Matlab,
C, VC, Java, perl, python, Basic, Fortran and even a few scripting languages
on Unix.  Even if OpenSCAD+ or OpenSCAD2 adopt function pointers (I use them
extensively in Matlab and C), typedef, object/solid handle/pointers, mutable
variables, etc etc.  Things that make OpenSCAD not nearly as convenient as
conventional procedural languages.  It's actually re-assuring OpenSCAD is
handicapped.  It motivates me to keep using the languages I'm familiar with
for math and engineering.  And only use OpenSCAD for 3D (printing) output.

If another still remember PostScript, I remember learning a tiny of of its
syntax and some commands. I remember being told PostScript can do
"anything".  And I remember tell myself, don't get sucked in, just fix the
thesis (so that the printer can accept it) and graduate and get out of
school.

In my work, I am making a prototype which involves over a hundred hexagons
arranged in a way based on the geodesic dome.  Now I don't know if it's
possible to realize this hexagonal geodesic in OpenSCAD.  Even if it's
possible I know for sure I can do it faster and more powerful in Matlab, so
I use Matlab to calculate the hexagons, have Matlab generate a module
hexs.scad which contain 100+ hexagonal cylinders.  And then a prototype.scad
that use<hexs.scad> and add the structural support, base, drill holes for
mounting screws and even imprint a logo on the base.

For my own selfish purpose, I'd rather spend time hacking together a
solution with all the available tools (of which OpenSCAD is but one)
((another being KraGle)) than prodding or telling someone smarter than me
how to do their things my way.

When I choose a tool, I look not only at its (advertised) features and
functions, I more often make a judgement on the user community + development
team.  OpenJSCAD and various other similar programmatic CAD may have more
powerful features, but OpenSCAD is the only one enjoying a wide(ish) user
base and actively maintained and supported.  And I fear that some of the
radical changes being requested will destroy it.  Not due to technical
merits but human/societal factors.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14591.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

kintel spoted my mistake, x*z is non-affine so, sorry I was wrong on that point. I was thinking (I forgot the proper term until doug gave it) about perspective transformation which can be represented by a 4x4 matrix but not supported in OpenSCAD. But he also gave an important clue why a lot of this is loony ideas: kintel wrote > don’t support non-affine transformations because CGAL doesn’t. So yes, now that I've been better educated I remember at one point needing perspective transformation desperately and cursing OpenSCAD for not doing it for me. But after some attempts, I switch track to trying to solve my problem by some ways other than transformation. Of course there's no general solution to substituting a general perspective transformation with legal OpenSCAD commands, but I found a way to do exactly what I wanted to design at the time, printed it, published it and be done with it. I see OpenSCAD as a toy, a fantastic toy (hope no one takes offense). But it's not a proper programming language. If my design involves some complex math or algorithm, I would rather do the math in a language I normally use for math and engineering problems. I have written a ton of codes in Matlab, C, VC, Java, perl, python, Basic, Fortran and even a few scripting languages on Unix. Even if OpenSCAD+ or OpenSCAD2 adopt function pointers (I use them extensively in Matlab and C), typedef, object/solid handle/pointers, mutable variables, etc etc. Things that make OpenSCAD not nearly as convenient as conventional procedural languages. It's actually re-assuring OpenSCAD is handicapped. It motivates me to keep using the languages I'm familiar with for math and engineering. And only use OpenSCAD for 3D (printing) output. If another still remember PostScript, I remember learning a tiny of of its syntax and some commands. I remember being told PostScript can do "anything". And I remember tell myself, don't get sucked in, just fix the thesis (so that the printer can accept it) and graduate and get out of school. In my work, I am making a prototype which involves over a hundred hexagons arranged in a way based on the geodesic dome. Now I don't know if it's possible to realize this hexagonal geodesic in OpenSCAD. Even if it's possible I know for sure I can do it faster and more powerful in Matlab, so I use Matlab to calculate the hexagons, have Matlab generate a module hexs.scad which contain 100+ hexagonal cylinders. And then a prototype.scad that use<hexs.scad> and add the structural support, base, drill holes for mounting screws and even imprint a logo on the base. For my own selfish purpose, I'd rather spend time hacking together a solution with all the available tools (of which OpenSCAD is but one) ((another being KraGle)) than prodding or telling someone smarter than me how to do their things my way. When I choose a tool, I look not only at its (advertised) features and functions, I more often make a judgement on the user community + development team. OpenJSCAD and various other similar programmatic CAD may have more powerful features, but OpenSCAD is the only one enjoying a wide(ish) user base and actively maintained and supported. And I fear that some of the radical changes being requested will destroy it. Not due to technical merits but human/societal factors. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14591.html Sent from the OpenSCAD mailing list archive at Nabble.com.
T
Trygon
Tue, Nov 17, 2015 9:23 AM

The dark art of non affine transformations ;-) :

// Joukowsky airfoil
// circle -> airfoil, using a non affine transformation
// Trygon Nov2015

n=40; // number of facets
s=20; // scale factor
l=250; // wing length
ro=s/40; // offset radius (used to thicken material around trailing edge
cusp)

x=-0.15;
y=0.15;
r=norm([1,0]-[x,y]);

/*
linear_extrude(height=200) offset(r=ro) scale([s,s,s])
transform()=[x*(xx+yy+1)/(xx+yy),y*(xx+yy-1)/(xx+yy)]
translate([x,y,0]) circle(r,$fn=n);
*/

// manually build vertex set for circle
p1=[for(i=[0:n-1]) let(a=i360/n) [rsin(a)+x,r*cos(a)+y]];

// transform vertex set
p2=[for(i=p1) [si[0](i[0]*i[0]+i[1]*i[1]+1)/(i[0]i[0]+i[1]i[1]),
s
i[1]
(i[0]*i[0]+i[1]*i[1]-1)/(i[0]*i[0]+i[1]*i[1])]];

linear_extrude(height=l) offset(r=ro) polygon(p2);

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14593.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

The dark art of non affine transformations ;-) : // Joukowsky airfoil // circle -> airfoil, using a non affine transformation // Trygon Nov2015 n=40; // number of facets s=20; // scale factor l=250; // wing length ro=s/40; // offset radius (used to thicken material around trailing edge cusp) x=-0.15; y=0.15; r=norm([1,0]-[x,y]); /* linear_extrude(height=200) offset(r=ro) scale([s,s,s]) transform()=[x*(x*x+y*y+1)/(x*x+y*y),y*(x*x+y*y-1)/(x*x+y*y)] translate([x,y,0]) circle(r,$fn=n); */ // manually build vertex set for circle p1=[for(i=[0:n-1]) let(a=i*360/n) [r*sin(a)+x,r*cos(a)+y]]; // transform vertex set p2=[for(i=p1) [s*i[0]*(i[0]*i[0]+i[1]*i[1]+1)/(i[0]*i[0]+i[1]*i[1]), s*i[1]*(i[0]*i[0]+i[1]*i[1]-1)/(i[0]*i[0]+i[1]*i[1])]]; linear_extrude(height=l) offset(r=ro) polygon(p2); -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14593.html Sent from the OpenSCAD mailing list archive at Nabble.com.
AC
Alan Cox
Tue, Nov 17, 2015 10:05 AM

For my own selfish purpose, I'd rather spend time hacking together a
solution with all the available tools (of which OpenSCAD is but one)
((another being KraGle)) than prodding or telling someone smarter than me
how to do their things my way.

Likewise I mostly use other tools to output OpenSCAD object
representations. Having OpenSCAD to do the grunt work is brilliant and if

  • ok when - I need to debug the results of my programs it the UI and the
    integration are great. Some stuff I use ImplicitCAD for because OpenSCAD
    really can't handle the object, but my choice is definitely OpenSCAD.

I could in theory do it all in OpenSCAD but it would be ugly and probably
I would need to add the ability to bend a 3D object to a path for some of
the stuff I generate.

I'd also rather keep the stranger things I need to do from messing up
OpenSCAD for novices, and losing its friendly, easy to get nature for
beginners - especially non programmers. Lots of people need a beginner 3D
design tool, not many people need tools for generating model railway
carriage shells to match etched brass sides 8)

Alan

> For my own selfish purpose, I'd rather spend time hacking together a > solution with all the available tools (of which OpenSCAD is but one) > ((another being KraGle)) than prodding or telling someone smarter than me > how to do their things my way. > Likewise I mostly use other tools to output OpenSCAD object representations. Having OpenSCAD to do the grunt work is brilliant and if - ok when - I need to debug the results of my programs it the UI and the integration are great. Some stuff I use ImplicitCAD for because OpenSCAD really can't handle the object, but my choice is definitely OpenSCAD. I could in theory do it all in OpenSCAD but it would be ugly and probably I would need to add the ability to bend a 3D object to a path for some of the stuff I generate. I'd also rather keep the stranger things I need to do from messing up OpenSCAD for novices, and losing its friendly, easy to get nature for beginners - especially non programmers. Lots of people need a beginner 3D design tool, not many people need tools for generating model railway carriage shells to match etched brass sides 8) Alan
RW
Rob Ward
Tue, Nov 17, 2015 11:34 AM

That is very cool!!!

On 17/11/15 20:23, Trygon wrote:

The dark art of non affine transformations ;-) :

// Joukowsky airfoil
// circle -> airfoil, using a non affine transformation
// Trygon Nov2015

n=40; // number of facets
s=20; // scale factor
l=250; // wing length
ro=s/40; // offset radius (used to thicken material around trailing edge
cusp)

x=-0.15;
y=0.15;
r=norm([1,0]-[x,y]);

/*
linear_extrude(height=200) offset(r=ro) scale([s,s,s])
transform()=[x*(xx+yy+1)/(xx+yy),y*(xx+yy-1)/(xx+yy)]
translate([x,y,0]) circle(r,$fn=n);
*/

// manually build vertex set for circle
p1=[for(i=[0:n-1]) let(a=i360/n) [rsin(a)+x,r*cos(a)+y]];

// transform vertex set
p2=[for(i=p1) [si[0](i[0]*i[0]+i[1]*i[1]+1)/(i[0]i[0]+i[1]i[1]),
s
i[1]
(i[0]*i[0]+i[1]*i[1]-1)/(i[0]*i[0]+i[1]*i[1])]];

linear_extrude(height=l) offset(r=ro) polygon(p2);

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14593.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

That is very cool!!! On 17/11/15 20:23, Trygon wrote: > The dark art of non affine transformations ;-) : > > // Joukowsky airfoil > // circle -> airfoil, using a non affine transformation > // Trygon Nov2015 > > n=40; // number of facets > s=20; // scale factor > l=250; // wing length > ro=s/40; // offset radius (used to thicken material around trailing edge > cusp) > > x=-0.15; > y=0.15; > r=norm([1,0]-[x,y]); > > /* > linear_extrude(height=200) offset(r=ro) scale([s,s,s]) > transform()=[x*(x*x+y*y+1)/(x*x+y*y),y*(x*x+y*y-1)/(x*x+y*y)] > translate([x,y,0]) circle(r,$fn=n); > */ > > // manually build vertex set for circle > p1=[for(i=[0:n-1]) let(a=i*360/n) [r*sin(a)+x,r*cos(a)+y]]; > > // transform vertex set > p2=[for(i=p1) [s*i[0]*(i[0]*i[0]+i[1]*i[1]+1)/(i[0]*i[0]+i[1]*i[1]), > s*i[1]*(i[0]*i[0]+i[1]*i[1]-1)/(i[0]*i[0]+i[1]*i[1])]]; > > linear_extrude(height=l) offset(r=ro) polygon(p2); > > > > > -- > View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14593.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org >
T
Trygon
Tue, Nov 17, 2015 11:37 AM

Just because a command exists, doesn't mean you have to use it.

If the command transform() existed in OpenSCAD, I wouldn't include it in an
example intended for a beginner, nor would I include multmatrix() which also
has immense geometry mangling capability!

If OpenSCAD was to be made "safe" for beginners, I think the polygon() &
polyhedron() commands would need to be removed for starters, since they
expose vertex data... where would this end?

Books on C programming don't start with pointer arithmetic. In fact
Kernighan & Ritchie state, "Pointers ... [are] a marvelous way to create
impossible-to-understand programs ... however, pointers can also be used to
achieve clarity and simplicity."  I think this sums up the potential of an
OpenSCAD transform() command: powerful, but dangerous if used without care.

-Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14596.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Just because a command exists, doesn't mean you have to use it. If the command transform() existed in OpenSCAD, I wouldn't include it in an example intended for a beginner, nor would I include multmatrix() which also has immense geometry mangling capability! If OpenSCAD was to be made "safe" for beginners, I think the polygon() & polyhedron() commands would need to be removed for starters, since they expose vertex data... where would this end? Books on C programming don't start with pointer arithmetic. In fact Kernighan & Ritchie state, "Pointers ... [are] a marvelous way to create impossible-to-understand programs ... however, pointers can also be used to achieve clarity and simplicity." I think this sums up the potential of an OpenSCAD transform() command: powerful, but dangerous if used without care. -Trygon -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14596.html Sent from the OpenSCAD mailing list archive at Nabble.com.
P
Parkinbot
Tue, Nov 17, 2015 12:30 PM

Having followed this thread now for a while, I can see that obviously many of
us are trying to merge stuff implemented in several languages with OpenSCAD
and vice versa. One might call it loony stuff, but isn't a programming
language meant for being able to do loony stuff, without being loony itself?

The usual affine (and also some non affine) stuff can also be done with
other CAD programs by people, who love to drag around things with their
mouse. So there is an urgent need for more flexibility in a programming
language. And to be honest, the way functions and loops are expressed in
OpenSCAD is even more loony than in most programming languages that have
crossed my way in 35 years of programming. Prolog seems to be closest to it,
but this code is somehow better readable. I know that declarative
programming has its pros and cons, so please don't understand this as severe
criticism. It has been done great job so far, and a steadily growing
community is a good proof for this.

But as we are talking here about new features, their impact to the language
and how to use and implement them, it gets more and more clear to me that
OpenSCAD either needs more expressive power in terms of function and include
flexibility or minimum an API-function allowing to access library stuff
implemented in other languages. This service could be started on the basis
of a function prototype allowing for input and output of vectors only (maybe
also for strings) and lead to a steadily growing OpenSCAD automation model
with client and server functionality.
For now people like Kintel and me output .scad files from Matlab or other
high level languages to at least import vectors or other programmatic stuff,
that cannot be expressed in OpenSCAD with reasonable effort.
I'm currently doing a hard job implementing multidimensional cubic spline
functionality in OpenSCAD, which you get in Matlab with three lines, using
cscvn() or with five lines using 2D cubic splines. My aim is to escape
affinity and to be able to sweep around parametrized 2D-airfoil data in 3D
space and get smooth transitions between different parameter sets, without
having to code it the very hard way, as I have done it in
http://www.thingiverse.com/thing:900137
http://www.thingiverse.com/thing:900137

This is what I get out of a 7 by 4 vector using spline interpolation to
sweep around circles:

http://forum.openscad.org/file/n14597/loony.png

Loony stuff, especially when you think about using it n-dimensional for
other shapes like airfoils, gears and so on. But isn't it, what programmers
want to do and why programmers are programmers and not users?

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14597.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Having followed this thread now for a while, I can see that obviously many of us are trying to merge stuff implemented in several languages with OpenSCAD and vice versa. One might call it loony stuff, but isn't a programming language meant for being able to do loony stuff, without being loony itself? The usual affine (and also some non affine) stuff can also be done with other CAD programs by people, who love to drag around things with their mouse. So there is an urgent need for more flexibility in a programming language. And to be honest, the way functions and loops are expressed in OpenSCAD is even more loony than in most programming languages that have crossed my way in 35 years of programming. Prolog seems to be closest to it, but this code is somehow better readable. I know that declarative programming has its pros and cons, so please don't understand this as severe criticism. It has been done great job so far, and a steadily growing community is a good proof for this. But as we are talking here about new features, their impact to the language and how to use and implement them, it gets more and more clear to me that OpenSCAD either needs more expressive power in terms of function and include flexibility or minimum an API-function allowing to access library stuff implemented in other languages. This service could be started on the basis of a function prototype allowing for input and output of vectors only (maybe also for strings) and lead to a steadily growing OpenSCAD automation model with client and server functionality. For now people like Kintel and me output .scad files from Matlab or other high level languages to at least import vectors or other programmatic stuff, that cannot be expressed in OpenSCAD with reasonable effort. I'm currently doing a hard job implementing multidimensional cubic spline functionality in OpenSCAD, which you get in Matlab with three lines, using cscvn() or with five lines using 2D cubic splines. My aim is to escape affinity and to be able to sweep around parametrized 2D-airfoil data in 3D space and get smooth transitions between different parameter sets, without having to code it the very hard way, as I have done it in http://www.thingiverse.com/thing:900137 <http://www.thingiverse.com/thing:900137> This is what I get out of a 7 by 4 vector using spline interpolation to sweep around circles: <http://forum.openscad.org/file/n14597/loony.png> Loony stuff, especially when you think about using it n-dimensional for other shapes like airfoils, gears and so on. But isn't it, what programmers want to do and why programmers are programmers and not users? -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14597.html Sent from the OpenSCAD mailing list archive at Nabble.com.
J
jon
Tue, Nov 17, 2015 12:46 PM

I love the "organic" sense of the PNG you provided.  While others in
this group have come up with organic shapes with apparent ease, this is
one area where I struggle.  I look forward to learning more about the
tools you are using and creating.

Thank you!

Jon

On 11/17/2015 7:30 AM, Parkinbot wrote:

Having followed this thread now for a while, I can see that obviously many of
us are trying to merge stuff implemented in several languages with OpenSCAD
and vice versa. One might call it loony stuff, but isn't a programming
language meant for being able to do loony stuff, without being loony itself?

The usual affine (and also some non affine) stuff can also be done with
other CAD programs by people, who love to drag around things with their
mouse. So there is an urgent need for more flexibility in a programming
language. And to be honest, the way functions and loops are expressed in
OpenSCAD is even more loony than in most programming languages that have
crossed my way in 35 years of programming. Prolog seems to be closest to it,
but this code is somehow better readable. I know that declarative
programming has its pros and cons, so please don't understand this as severe
criticism. It has been done great job so far, and a steadily growing
community is a good proof for this.

But as we are talking here about new features, their impact to the language
and how to use and implement them, it gets more and more clear to me that
OpenSCAD either needs more expressive power in terms of function and include
flexibility or minimum an API-function allowing to access library stuff
implemented in other languages. This service could be started on the basis
of a function prototype allowing for input and output of vectors only (maybe
also for strings) and lead to a steadily growing OpenSCAD automation model
with client and server functionality.
For now people like Kintel and me output .scad files from Matlab or other
high level languages to at least import vectors or other programmatic stuff,
that cannot be expressed in OpenSCAD with reasonable effort.
I'm currently doing a hard job implementing multidimensional cubic spline
functionality in OpenSCAD, which you get in Matlab with three lines, using
cscvn() or with five lines using 2D cubic splines. My aim is to escape
affinity and to be able to sweep around parametrized 2D-airfoil data in 3D
space and get smooth transitions between different parameter sets, without
having to code it the very hard way, as I have done it in
http://www.thingiverse.com/thing:900137
http://www.thingiverse.com/thing:900137

This is what I get out of a 7 by 4 vector using spline interpolation to
sweep around circles:

http://forum.openscad.org/file/n14597/loony.png

Loony stuff, especially when you think about using it n-dimensional for
other shapes like airfoils, gears and so on. But isn't it, what programmers
want to do and why programmers are programmers and not users?

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14597.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org


No virus found in this message.
Checked by AVG - www.avg.com
Version: 2016.0.7227 / Virus Database: 4457/11015 - Release Date: 11/17/15

I love the "organic" sense of the PNG you provided. While others in this group have come up with organic shapes with apparent ease, this is one area where I struggle. I look forward to learning more about the tools you are using and creating. Thank you! Jon On 11/17/2015 7:30 AM, Parkinbot wrote: > Having followed this thread now for a while, I can see that obviously many of > us are trying to merge stuff implemented in several languages with OpenSCAD > and vice versa. One might call it loony stuff, but isn't a programming > language meant for being able to do loony stuff, without being loony itself? > > The usual affine (and also some non affine) stuff can also be done with > other CAD programs by people, who love to drag around things with their > mouse. So there is an urgent need for more flexibility in a programming > language. And to be honest, the way functions and loops are expressed in > OpenSCAD is even more loony than in most programming languages that have > crossed my way in 35 years of programming. Prolog seems to be closest to it, > but this code is somehow better readable. I know that declarative > programming has its pros and cons, so please don't understand this as severe > criticism. It has been done great job so far, and a steadily growing > community is a good proof for this. > > But as we are talking here about new features, their impact to the language > and how to use and implement them, it gets more and more clear to me that > OpenSCAD either needs more expressive power in terms of function and include > flexibility or minimum an API-function allowing to access library stuff > implemented in other languages. This service could be started on the basis > of a function prototype allowing for input and output of vectors only (maybe > also for strings) and lead to a steadily growing OpenSCAD automation model > with client and server functionality. > For now people like Kintel and me output .scad files from Matlab or other > high level languages to at least import vectors or other programmatic stuff, > that cannot be expressed in OpenSCAD with reasonable effort. > I'm currently doing a hard job implementing multidimensional cubic spline > functionality in OpenSCAD, which you get in Matlab with three lines, using > cscvn() or with five lines using 2D cubic splines. My aim is to escape > affinity and to be able to sweep around parametrized 2D-airfoil data in 3D > space and get smooth transitions between different parameter sets, without > having to code it the very hard way, as I have done it in > http://www.thingiverse.com/thing:900137 > <http://www.thingiverse.com/thing:900137> > > This is what I get out of a 7 by 4 vector using spline interpolation to > sweep around circles: > > <http://forum.openscad.org/file/n14597/loony.png> > > Loony stuff, especially when you think about using it n-dimensional for > other shapes like airfoils, gears and so on. But isn't it, what programmers > want to do and why programmers are programmers and not users? > > > > > -- > View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14597.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > > > ----- > No virus found in this message. > Checked by AVG - www.avg.com > Version: 2016.0.7227 / Virus Database: 4457/11015 - Release Date: 11/17/15 > >
C
clothbot
Tue, Nov 17, 2015 2:01 PM

Trygon wrote

Just because a command exists, doesn't mean you have to use it.

If the command transform() existed in OpenSCAD, I wouldn't include it in
an example intended for a beginner, nor would I include multmatrix() which
also has immense geometry mangling capability!

I disagree, but with the qualification that translate(), rotate(), scale(),
mirror() and multmatrix() should be introduced in the context of forward
kinematics (see https://en.wikipedia.org/wiki/Forward_kinematics).

Side note:  We really need a matrix inverse() function for completeness.
The eigen3 library which OpenSCAD makes use of has matrix inverse functions
(see
http://eigen.tuxfamily.org/dox/classEigen_1_1MatrixBase.html#aa2834da4c855fa35fed8c4030f79f9da),
along with other useful things like plane-to-plane intersection (see
http://eigen.tuxfamily.org/dox/classEigen_1_1Hyperplane.html#ad10ca15c93ee4d825f92a2c4563ed678).

The scale(), rotate(), mirror() and translate() operators can be thought of
as "convenience wrappers" for the general-purpose multmatrix() operator.  I
find multi-axis rotate() operations are easier to get a handle on if you
understand the order in which successive matrix multiplications are
happening -
https://github.com/openscad/openscad/blob/master/src/transform.cc#L119 - but
more often than not I'll break them up into explicit, single-axis rotate()
operations to keep track of where things are going.

Andrew.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14599.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Trygon wrote > Just because a command exists, doesn't mean you have to use it. > > If the command transform() existed in OpenSCAD, I wouldn't include it in > an example intended for a beginner, nor would I include multmatrix() which > also has immense geometry mangling capability! I disagree, but with the qualification that translate(), rotate(), scale(), mirror() and multmatrix() should be introduced in the context of forward kinematics (see https://en.wikipedia.org/wiki/Forward_kinematics). Side note: We *really* need a matrix inverse() function for completeness. The eigen3 library which OpenSCAD makes use of has matrix inverse functions (see http://eigen.tuxfamily.org/dox/classEigen_1_1MatrixBase.html#aa2834da4c855fa35fed8c4030f79f9da), along with other useful things like plane-to-plane intersection (see http://eigen.tuxfamily.org/dox/classEigen_1_1Hyperplane.html#ad10ca15c93ee4d825f92a2c4563ed678). The scale(), rotate(), mirror() and translate() operators can be thought of as "convenience wrappers" for the general-purpose multmatrix() operator. I find multi-axis rotate() operations are easier to get a handle on if you understand the order in which successive matrix multiplications are happening - https://github.com/openscad/openscad/blob/master/src/transform.cc#L119 - but more often than not I'll break them up into explicit, single-axis rotate() operations to keep track of where things are going. Andrew. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14599.html Sent from the OpenSCAD mailing list archive at Nabble.com.
C
ctchin
Wed, Nov 18, 2015 4:28 AM

Parkinbot wrote

Having followed this thread now for a while, I can see that obviously many
of us are trying to merge stuff implemented in several languages with
OpenSCAD and vice versa. One might call it loony stuff, but isn't a
programming language meant for being able to do loony stuff, without being
loony itself?
...
Loony stuff, especially when you think about using it n-dimensional for
other shapes like airfoils, gears and so on. But isn't it, what
programmers want to do and why programmers are programmers and not users?

Well not un-deliberately, my wording loony was a bit vague.  I love the NACA
you created and Joukowski (that's how my fluid mech book spells it) airfoil
Trygon created.  My point about loony isn't about amazing and beautiful
things that the users created (or better: may create) but too often some
users have some vague idea and expect OTHER people to do the hard work for
them.

In general conformal mapping is a powerful branch of math that make some
very useful shapes.

Especially you and Trygon's code showed the existing OpenSCAD commands are
powerful enough if only more people put some hard work into it.  I'd invite
you to put some of your code into a library that I'm advocating.

Now yes... you have been convincing there are room to expand some sort of
distortion, transformation or something in OpenSCAD (like I hinted at, I've
been frustrated with it myself).  But I'm not sure you have been convincing
enough that the core team should take on this task as priority, soon.

OpenSCAD is open source, there's an open invitation on the main website to
add new features.  This "debate" would be a lot more substantial if someone
create a new transformation and make a pitch that it should be included into
the main branch.

After seeing some substantive response to the "loony" challenge... I was
thinking how to enable some of the "loony" ideas to progress without
unwanted side-effects.  The answer seems obvious, create a plug-in
interface.

Surely it has been requested and discussed before... browsing the issues on
github... am I seeing it right?  It's not been posted as a new feature
request? Wonder if I should open a new thread on it...

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14611.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Parkinbot wrote > Having followed this thread now for a while, I can see that obviously many > of us are trying to merge stuff implemented in several languages with > OpenSCAD and vice versa. One might call it loony stuff, but isn't a > programming language meant for being able to do loony stuff, without being > loony itself? > ... > Loony stuff, especially when you think about using it n-dimensional for > other shapes like airfoils, gears and so on. But isn't it, what > programmers want to do and why programmers are programmers and not users? Well not un-deliberately, my wording loony was a bit vague. I love the NACA you created and Joukowski (that's how my fluid mech book spells it) airfoil Trygon created. My point about loony isn't about amazing and beautiful things that the users created (or better: may create) but too often some users have some vague idea and expect OTHER people to do the hard work for them. In general conformal mapping is a powerful branch of math that make some very useful shapes. Especially you and Trygon's code showed the existing OpenSCAD commands are powerful enough if only more people put some hard work into it. I'd invite you to put some of your code into a library that I'm advocating. Now yes... you have been convincing there are room to expand some sort of distortion, transformation or something in OpenSCAD (like I hinted at, I've been frustrated with it myself). But I'm not sure you have been convincing enough that the core team should take on this task as priority, soon. OpenSCAD is open source, there's an open invitation on the main website to add new features. This "debate" would be a lot more substantial if someone create a new transformation and make a pitch that it should be included into the main branch. After seeing some substantive response to the "loony" challenge... I was thinking how to enable some of the "loony" ideas to progress without unwanted side-effects. The answer seems obvious, create a plug-in interface. Surely it has been requested and discussed before... browsing the issues on github... am I seeing it right? It's not been posted as a new feature request? Wonder if I should open a new thread on it... -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14611.html Sent from the OpenSCAD mailing list archive at Nabble.com.
C
ctchin
Wed, Nov 18, 2015 4:36 AM

Parkinbot wrote

a hard job implementing multidimensional cubic spline functionality in
OpenSCAD, which you get in Matlab with three lines, using cscvn() or with
five lines using 2D cubic splines.

Totally beside the point: two months ago I challenged my grad student to
create a parametric model of a branching blood vessel on the 3D printer.
There's no progress so I pretty much forgot about it.

But your response to my "loony" charge gave me some crucial hints, I think I
can figure out the break-thru and the student can do the rest.  Hopefully I
will hold a model in my hands by Monday.

Thanks!

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14612.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Parkinbot wrote > a hard job implementing multidimensional cubic spline functionality in > OpenSCAD, which you get in Matlab with three lines, using cscvn() or with > five lines using 2D cubic splines. Totally beside the point: two months ago I challenged my grad student to create a parametric model of a branching blood vessel on the 3D printer. There's no progress so I pretty much forgot about it. But your response to my "loony" charge gave me some crucial hints, I think I can figure out the break-thru and the student can do the rest. Hopefully I will hold a model in my hands by Monday. Thanks! -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14612.html Sent from the OpenSCAD mailing list archive at Nabble.com.
T
Trygon
Wed, Nov 18, 2015 8:58 AM

The dark art of non affine transformations part II - Art (?) :

// this does not actually work, there is no transform() command at present!
transform()=let(sf1=1+sin(12atan2(y,x))/8, sf2=2+cos(z1.1+70))
[xsf1sf2, ysf1sf2, z] cylinder(h=300, r=50, center=true, $fn=240);

-Trygon

http://forum.openscad.org/file/n14615/TransformArt.png

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14615.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

The dark art of non affine transformations part II - Art (?) : // this does not actually work, there is no transform() command at present! transform()=let(sf1=1+sin(12*atan2(y,x))/8, sf2=2+cos(z*1.1+70)) [x*sf1*sf2, y*sf1*sf2, z] cylinder(h=300, r=50, center=true, $fn=240); -Trygon <http://forum.openscad.org/file/n14615/TransformArt.png> -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14615.html Sent from the OpenSCAD mailing list archive at Nabble.com.
T
Trygon
Wed, Nov 18, 2015 9:28 AM

The same non affine transformation applied to a different solid:

// this does not actually work, there is no transform() command at present!
transform()=let(sf1=1+sin(12atan2(y,x))/8, sf2=2+cos(z1.1+70))
[xsf1sf2, ysf1sf2, z] cube(size=[100, 100, 300], center=true);

http://forum.openscad.org/file/n14616/TransformArt2.png

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14616.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

The same non affine transformation applied to a different solid: // this does not actually work, there is no transform() command at present! transform()=let(sf1=1+sin(12*atan2(y,x))/8, sf2=2+cos(z*1.1+70)) [x*sf1*sf2, y*sf1*sf2, z] cube(size=[100, 100, 300], center=true); <http://forum.openscad.org/file/n14616/TransformArt2.png> -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14616.html Sent from the OpenSCAD mailing list archive at Nabble.com.
C
ctchin
Wed, Nov 18, 2015 12:17 PM

You could also do  some nice things without non-affine transformation.

Thanks to the warm discussion, I spent my day (not quite 7 hours of coding)
making the blood vessel I wanted 2 months ago.  Sometimes all it take is
some determination.

~80 lines of code (with comments) gave me what I needed, without even
resorting to Matlab.

Pushing 200 lines of code if I kept all the debugging/evolving codes in
place.  Note that the pipe diameter changes along the pipe length, the wall
thickness is very nearly uniform.

Plus now I have a new library for making cylinders and pipes along an
arbitrary (but not too crazy) curve.

http://forum.openscad.org/file/n14618/bifurcation.jpg
http://forum.openscad.org/file/n14618/bifurcation-cutaway.jpg

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14618.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

You could also do some nice things without non-affine transformation. Thanks to the warm discussion, I spent my day (not quite 7 hours of coding) making the blood vessel I wanted 2 months ago. Sometimes all it take is some determination. ~80 lines of code (with comments) gave me what I needed, without even resorting to Matlab. Pushing 200 lines of code if I kept all the debugging/evolving codes in place. Note that the pipe diameter changes along the pipe length, the wall thickness is very nearly uniform. Plus now I have a new library for making cylinders and pipes along an arbitrary (but not too crazy) curve. <http://forum.openscad.org/file/n14618/bifurcation.jpg> <http://forum.openscad.org/file/n14618/bifurcation-cutaway.jpg> -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14618.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Wed, Nov 18, 2015 2:13 PM

The proposed tranform() module is awesome, no doubt.

If this gets implemented before OpenSCAD2, then I would like the syntax to
be forward compatible with OpenSCAD2. Like this:

transform(
f(x,y,z)=
let (sf1=1+sin(12atan2(y,x))/8, sf2=2+cos(z1.1+70))
[xsf1sf2, ysf1sf2, z] )
cube(size=[100, 100, 300], center=true);

On 18 November 2015 at 04:28, Trygon db5765@outlook.com wrote:

The same non affine transformation applied to a different solid:

// this does not actually work, there is no transform() command at present!
transform()=let(sf1=1+sin(12atan2(y,x))/8, sf2=2+cos(z1.1+70))
[xsf1sf2, ysf1sf2, z] cube(size=[100, 100, 300], center=true);

http://forum.openscad.org/file/n14616/TransformArt2.png

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14616.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

The proposed tranform() module is awesome, no doubt. If this gets implemented before OpenSCAD2, then I would like the syntax to be forward compatible with OpenSCAD2. Like this: transform( f(x,y,z)= let (sf1=1+sin(12*atan2(y,x))/8, sf2=2+cos(z*1.1+70)) [x*sf1*sf2, y*sf1*sf2, z] ) cube(size=[100, 100, 300], center=true); On 18 November 2015 at 04:28, Trygon <db5765@outlook.com> wrote: > The same non affine transformation applied to a different solid: > > // this does not actually work, there is no transform() command at present! > transform()=let(sf1=1+sin(12*atan2(y,x))/8, sf2=2+cos(z*1.1+70)) > [x*sf1*sf2, y*sf1*sf2, z] cube(size=[100, 100, 300], center=true); > > <http://forum.openscad.org/file/n14616/TransformArt2.png> > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14616.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
R
runsun
Wed, Nov 18, 2015 2:47 PM

ctchin wrote

~80 lines of code (with comments) gave me what I needed, without even
resorting to Matlab.

Pushing 200 lines of code if I kept all the debugging/evolving codes in
place.  Note that the pipe diameter changes along the pipe length, the
wall thickness is very nearly uniform.

Plus now I have a new library for making cylinders and pipes along an
arbitrary (but not too crazy) curve.

Can you share how you join the two tubes? partial code would be even better.


$  Runsun Pan, PhD

$ libs:

doctest ,

faces ( git ),

offline doc ( git ),

runscad.py( 1 , 2 , git );

$ tips:

hash( 1 , 2 ),

sweep ,

var( 1 , 2 ),

lerp ,

animGif ,

precision

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14620.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

ctchin wrote > ~80 lines of code (with comments) gave me what I needed, without even > resorting to Matlab. > > Pushing 200 lines of code if I kept all the debugging/evolving codes in > place. Note that the pipe diameter changes along the pipe length, the > wall thickness is very nearly uniform. > > Plus now I have a new library for making cylinders and pipes along an > arbitrary (but not too crazy) curve. Can you share how you join the two tubes? partial code would be even better. ----- $ Runsun Pan, PhD $ libs: doctest , faces ( git ), offline doc ( git ), runscad.py( 1 , 2 , git ); $ tips: hash( 1 , 2 ), sweep , var( 1 , 2 ), lerp , animGif , precision -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14620.html Sent from the OpenSCAD mailing list archive at Nabble.com.
MK
Marius Kintel
Wed, Nov 18, 2015 4:02 PM

Trygon,

We’ve been compiling some demos of what can be done in user space by manually managing vertices:
https://github.com/openscad/list-comprehension-demos

This is more of a playground to explore what sort of functionality should be built into OpenSCAD.

For these demos, we currently only use 2D object as basis, see https://github.com/openscad/scad-utils/blob/master/shapes.scad

It would be cool to add some of your experiments to this repository, for purpose of creating a join exploratory playground until we land on a good interface for this kind of functionality.

Cheers,

-Marius

Trygon, We’ve been compiling some demos of what can be done in user space by manually managing vertices: https://github.com/openscad/list-comprehension-demos This is more of a playground to explore what sort of functionality should be built into OpenSCAD. For these demos, we currently only use 2D object as basis, see https://github.com/openscad/scad-utils/blob/master/shapes.scad It would be cool to add some of your experiments to this repository, for purpose of creating a join exploratory playground until we land on a good interface for this kind of functionality. Cheers, -Marius
C
ctchin
Wed, Nov 18, 2015 7:03 PM

Heheh, I guess you have asked for the crucial trick.  The question is how to
join two cylinders at an angle with a satisfactory "elbow".  Once you
figured that, the rest is just putting the Lego pieces together to make
cylinders and pipes along any paths.  Branching also becomes obvious.

The following code is robust, except for one factor: h=2*d0, the factor 2 is
arbitrary and will fail if angle is too small.  It's easy enough to fix, but
I've decided to finish working on my branching vessels rather than fix a
problem that only happens with unnatural-looking kinks.

The color("red") is obviously unnecessary, it's just to show the important
"elbow".

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14626.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Heheh, I guess you have asked for the crucial trick. The question is how to join two cylinders at an angle with a satisfactory "elbow". Once you figured that, the rest is just putting the Lego pieces together to make cylinders and pipes along any paths. Branching also becomes obvious. The following code is robust, except for one factor: h=2*d0, the factor 2 is arbitrary and will fail if angle is too small. It's easy enough to fix, but I've decided to finish working on my branching vessels rather than fix a problem that only happens with unnatural-looking kinks. The color("red") is obviously unnecessary, it's just to show the important "elbow". -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14626.html Sent from the OpenSCAD mailing list archive at Nabble.com.
P
Parkinbot
Wed, Nov 18, 2015 8:55 PM

If I was a pipe I'd prefer to be modelled like this (works for any angle ):

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14627.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

If I was a pipe I'd prefer to be modelled like this (works for any angle ): -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14627.html Sent from the OpenSCAD mailing list archive at Nabble.com.
R
runsun
Wed, Nov 18, 2015 10:11 PM

Thx, ctchin. That's neat.

Since I spent most of design in polyhedron, what I am most interested in is
how two polyhedrons join/branch.


$  Runsun Pan, PhD

$ libs:

doctest ,

faces ( git ),

offline doc ( git ),

runscad.py( 1 , 2 , git );

$ tips:

hash( 1 , 2 ),

sweep ,

var( 1 , 2 ),

lerp ,

animGif ,

precision

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14633.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Thx, ctchin. That's neat. Since I spent most of design in polyhedron, what I am most interested in is how two polyhedrons join/branch. ----- $ Runsun Pan, PhD $ libs: doctest , faces ( git ), offline doc ( git ), runscad.py( 1 , 2 , git ); $ tips: hash( 1 , 2 ), sweep , var( 1 , 2 ), lerp , animGif , precision -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14633.html Sent from the OpenSCAD mailing list archive at Nabble.com.
R
runsun
Wed, Nov 18, 2015 10:21 PM

btw, ctchin, posts in this thread,  Bent rod
http://forum.openscad.org/Bent-rod-tp14003p14004.html  , might give some
ideas. Among them, my version:

http://forum.openscad.org/file/n14004/20150925_bent_pipe.png


$  Runsun Pan, PhD

$ libs:

doctest ,

faces ( git ),

offline doc ( git ),

runscad.py( 1 , 2 , git );

$ tips:

hash( 1 , 2 ),

sweep ,

var( 1 , 2 ),

lerp ,

animGif ,

precision

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14634.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

btw, ctchin, posts in this thread, Bent rod <http://forum.openscad.org/Bent-rod-tp14003p14004.html> , might give some ideas. Among them, my version: <http://forum.openscad.org/file/n14004/20150925_bent_pipe.png> ----- $ Runsun Pan, PhD $ libs: doctest , faces ( git ), offline doc ( git ), runscad.py( 1 , 2 , git ); $ tips: hash( 1 , 2 ), sweep , var( 1 , 2 ), lerp , animGif , precision -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14634.html Sent from the OpenSCAD mailing list archive at Nabble.com.
N
Neon22
Thu, Nov 19, 2015 2:12 AM

ctchin wrote

Branching also becomes obvious.

Parkinbot wrote

If I was a pipe I'd prefer to be modelled like this (works for any angle

):

I was playing with these two approaches and tried to make a generalized tree
branching with fillets between.

Its working well for direct code but I wanted to use a list and a for loop.
Alas the for loop does an implied union() and so the children() is not
working.
My brain has frozen on how to get around it.
E.g. I have this: (images in forum)

use <fillet.scad>
// from clothbot
// - https://github.com/clothbot/ClothBotCreations/tree/master/utilities

d0 = 10;
h1 = 30;
h2 = 20;
angle = -66;

// Parkinbot approach (filleted)
translate([30,20,0])
fillet(r=2,steps=2) {
rotate([angle,0,0])
cylinder(h1, d=d0);
cylinder(h2, d=d0);
// join
color("red")
sphere(d0/2);
}

// ctchin approach (filleted)
translate([30,-20,0])
fillet(r=2,steps=4) {
rotate([angle,0,0]) cylinder(h1, d=d0);
cylinder(h2, d=d0);
// join
color("red")
intersection() {
rotate([angle,0,0])
translate([0,0,-2d0])
cylinder(d=d0,h=2
d0);
translate([0,0,-2d0])
cylinder(d=d0,h=2
d0);
}
}

//-----------------------------
// Each branch is a cylinder with [diameter, startpt, anglexyz, length]
//    - startpt, anglexyz are triplets
// generalize later to use shape profile instead of circle (cylinder)
// (one day alllow random variation in deformation along length of the
branch object)
branches = [
[10, [0,0,0], [0,0,0], 40],
[10, [0,0,0], [45,0,0], 40],
[5,  [0,0,30], [66,-22,0], 33],
[5,  [0,0,25], [66,-22,250], 33],
];

module make_tree(branches=branches, blend=4, method="round") {
// add round/sharp in here
// how to get around implied union of for() ?
fillet(r=2,steps=4) {
for (b=branches) {
dia = b[0];
start = b[1];
angle = b[2];
dist = b[3];
translate(start)
rotate(angle)
cylinder(h=dist, d=dia);
}
}
}

make_tree();

To get a result like this:
http://forum.openscad.org/file/n14635/branches_5.png

How do I pass all the results of the for loop to fillet() as children ?

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14635.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

ctchin wrote > Branching also becomes obvious. Parkinbot wrote > If I was a pipe I'd prefer to be modelled like this (works for any angle > ): I was playing with these two approaches and tried to make a generalized tree branching with fillets between. Its working well for direct code but I wanted to use a list and a for loop. Alas the for loop does an implied union() and so the children() is not working. My brain has frozen on how to get around it. E.g. I have this: (images in forum) use <fillet.scad> // from clothbot // - https://github.com/clothbot/ClothBotCreations/tree/master/utilities d0 = 10; h1 = 30; h2 = 20; angle = -66; // Parkinbot approach (filleted) translate([30,20,0]) fillet(r=2,steps=2) { rotate([angle,0,0]) cylinder(h1, d=d0); cylinder(h2, d=d0); // join color("red") sphere(d0/2); } // ctchin approach (filleted) translate([30,-20,0]) fillet(r=2,steps=4) { rotate([angle,0,0]) cylinder(h1, d=d0); cylinder(h2, d=d0); // join color("red") intersection() { rotate([angle,0,0]) translate([0,0,-2*d0]) cylinder(d=d0,h=2*d0); translate([0,0,-2*d0]) cylinder(d=d0,h=2*d0); } } //----------------------------- // Each branch is a cylinder with [diameter, startpt, anglexyz, length] // - startpt, anglexyz are triplets // generalize later to use shape profile instead of circle (cylinder) // (one day alllow random variation in deformation along length of the branch object) branches = [ [10, [0,0,0], [0,0,0], 40], [10, [0,0,0], [45,0,0], 40], [5, [0,0,30], [66,-22,0], 33], [5, [0,0,25], [66,-22,250], 33], ]; module make_tree(branches=branches, blend=4, method="round") { // add round/sharp in here // how to get around implied union of for() ? fillet(r=2,steps=4) { for (b=branches) { dia = b[0]; start = b[1]; angle = b[2]; dist = b[3]; translate(start) rotate(angle) cylinder(h=dist, d=dia); } } } make_tree(); To get a result like this: <http://forum.openscad.org/file/n14635/branches_5.png> How do I pass all the results of the for loop to fillet() as children ? -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14635.html Sent from the OpenSCAD mailing list archive at Nabble.com.
P
Parkinbot
Thu, Nov 19, 2015 2:17 AM

Usually, an (implicit) union joins overlapping or matching (there is always a
numerical error!) objects. This happens also with polyhedrons. If you
calculate your own polyhedrons (your example doesn't look so) just provide
some very small overlapping.
BUT, when I try to implement your example along the "broadway", say, like
this:

I'm getting this:
http://forum.openscad.org/file/n14636/weird.png

I remember that the convexity parameter of linear_extrude() never worked
properly with me, so in the end to get more out of it I implemented a
fullblown library to bypass it on the basis of hull(). Just have a look at:
http://www.thingiverse.com/thing:648813

runsun wrote

btw, ctchin, posts in this thread,
Bent rod http://forum.openscad.org/Bent-rod-tp14003p14004.html
, might give some ideas. Among them, my version:

http://forum.openscad.org/file/n14004/20150925_bent_pipe.png

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14636.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Usually, an (implicit) union joins overlapping or matching (there is always a numerical error!) objects. This happens also with polyhedrons. If you calculate your own polyhedrons (your example doesn't look so) just provide some very small overlapping. BUT, when I try to implement your example along the "broadway", say, like this: I'm getting this: <http://forum.openscad.org/file/n14636/weird.png> I remember that the convexity parameter of linear_extrude() never worked properly with me, so in the end to get more out of it I implemented a fullblown library to bypass it on the basis of hull(). Just have a look at: http://www.thingiverse.com/thing:648813 runsun wrote > btw, ctchin, posts in this thread, > Bent rod <http://forum.openscad.org/Bent-rod-tp14003p14004.html> > , might give some ideas. Among them, my version: <http://forum.openscad.org/file/n14004/20150925_bent_pipe.png> -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14636.html Sent from the OpenSCAD mailing list archive at Nabble.com.
P
Parkinbot
Thu, Nov 19, 2015 3:01 AM

@Neon: If something is against you, better try to befriend it.
OK, I know, this is more a work around than the solution you are seeking,
but I'm afraid you won't get rid of the implicit union.

http://forum.openscad.org/file/n14637/tree.png

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14637.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

@Neon: If something is against you, better try to befriend it. OK, I know, this is more a work around than the solution you are seeking, but I'm afraid you won't get rid of the implicit union. <http://forum.openscad.org/file/n14637/tree.png> -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14637.html Sent from the OpenSCAD mailing list archive at Nabble.com.
N
Neon22
Thu, Nov 19, 2015 5:10 AM

ok that's pretty nice.
I guess the disadvantage is the exponential work done as each fillet is
applied to the growing object and one new part.
Maybe in OpenSCAD2 .
Thanks...

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14638.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

ok that's pretty nice. I guess the disadvantage is the exponential work done as each fillet is applied to the growing object and one new part. Maybe in OpenSCAD2 . Thanks... -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14638.html Sent from the OpenSCAD mailing list archive at Nabble.com.
C
ctchin
Thu, Nov 19, 2015 6:20 AM

Parkinbot wrote

  • SMACK FOREHEAD *

Doh of course you are right!  My brain was stuck from a previous design for
which the sphere wouldn't work, but for cylinders of course a spherical
elbow is easier and prettier.

THANKS!

(anyway the model with the ugly angular joints already went and come back
from the printer)

http://forum.openscad.org/file/n14639/bifurcation-printed.jpg

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14639.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Parkinbot wrote * SMACK FOREHEAD * Doh of course you are right! My brain was stuck from a previous design for which the sphere wouldn't work, but for cylinders of course a spherical elbow is easier and prettier. THANKS! (anyway the model with the ugly angular joints already went and come back from the printer) <http://forum.openscad.org/file/n14639/bifurcation-printed.jpg> -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14639.html Sent from the OpenSCAD mailing list archive at Nabble.com.
P
Parkinbot
Thu, Nov 19, 2015 1:03 PM

You are right. A better solution would be the following approach. I didn't
present it, as I forgot how to express a partial array (Was it ever possible
in OpenSCAD to express a partial array like branches[2:4] ) Overcoming this
obstacle with the tail function, this is your proper and fast solution
ver2.0:

(By the way: a nice approach .)

Neon22 wrote

I guess the disadvantage is the exponential work done as each fillet is
applied to the growing object and one new part.

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14644.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

You are right. A better solution would be the following approach. I didn't present it, as I forgot how to express a partial array (Was it ever possible in OpenSCAD to express a partial array like branches[2:4] ) Overcoming this obstacle with the tail function, this is your proper and fast solution ver2.0: (By the way: a nice approach .) Neon22 wrote > I guess the disadvantage is the exponential work done as each fillet is > applied to the growing object and one new part. -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14644.html Sent from the OpenSCAD mailing list archive at Nabble.com.
MS
Mark Schafer
Thu, Nov 19, 2015 10:18 PM

Yes I used this pattern
for (i=[1:len(branches)]) {
b = branches[i];

On 11/20/2015 2:03 AM, Parkinbot wrote:

You are right. A better solution would be the following approach. I didn't
present it, as I forgot how to express a partial array (Was it ever possible
in OpenSCAD to express a partial array like branches[2:4] ) Overcoming this
obstacle with the tail function, this is your proper and fast solution
ver2.0:

(By the way: a nice approach .)

Yes I used this pattern for (i=[1:len(branches)]) { b = branches[i]; On 11/20/2015 2:03 AM, Parkinbot wrote: > You are right. A better solution would be the following approach. I didn't > present it, as I forgot how to express a partial array (Was it ever possible > in OpenSCAD to express a partial array like branches[2:4] ) Overcoming this > obstacle with the tail function, this is your proper and fast solution > ver2.0: > > (By the way: a nice approach .) > >
DM
doug moen
Thu, Nov 19, 2015 11:04 PM

parkinbot: Was it ever possible in OpenSCAD to express a partial array like
branches[2:4]?

Currently you must write
[for(i=[2:4])branches[i]]

Many people have asked for a more direct 'slice' operator, but we don't
have one yet. Multiple syntaxes have been proposed.

On 19 November 2015 at 08:03, Parkinbot rudolf@parkinbot.com wrote:

You are right. A better solution would be the following approach. I didn't
present it, as I forgot how to express a partial array (Was it ever
possible
in OpenSCAD to express a partial array like branches[2:4] ) Overcoming this
obstacle with the tail function, this is your proper and fast solution
ver2.0:

(By the way: a nice approach .)

Neon22 wrote

I guess the disadvantage is the exponential work done as each fillet is
applied to the growing object and one new part.

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p14644.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

parkinbot: Was it ever possible in OpenSCAD to express a partial array like branches[2:4]? Currently you must write [for(i=[2:4])branches[i]] Many people have asked for a more direct 'slice' operator, but we don't have one yet. Multiple syntaxes have been proposed. On 19 November 2015 at 08:03, Parkinbot <rudolf@parkinbot.com> wrote: > You are right. A better solution would be the following approach. I didn't > present it, as I forgot how to express a partial array (Was it ever > possible > in OpenSCAD to express a partial array like branches[2:4] ) Overcoming this > obstacle with the tail function, this is your proper and fast solution > ver2.0: > > (By the way: a nice approach .) > > > > > Neon22 wrote > > I guess the disadvantage is the exponential work done as each fillet is > > applied to the growing object and one new part. > > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p14644.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
T
Trygon
Sun, Dec 6, 2015 9:52 PM

The dark art of non affine transformations part III, solution to:

http://forum.openscad.org/Wave-spring-tp14948.html

Cheers,
Trygon

PS for documentation on function fa() see
http://forum.openscad.org/fe-Tolerance-based-arc-approximation-tp14212.html

// Trygon Dec2015 - non affine transformation: washer -> spring washer

$fe=0.01;

ro=10; // outside radius
ri=5; // hole radius
h=1; // washer thickness
hw=2; // wave height
nw=3; // number of waves

washer=WasherObject(ro,ri,h);
polyhedron(TransformPoints(washer[0],hw,nw),washer[1]);

function WasherObject(ro,ri,h) = let(
n=ceil(360/fa(ro)), // number of segments
p0=[for(i=[0:n-1]) let(a=i360/n) [rocos(a),rosin(a),h/2]],
p1=[for(i=p0) [i[0]ri/ro,i[1]ri/ro,i[2]]],
p2=[for(i=p0) [i[0],i[1],-h/2]],
p3=[for(i=p1) [i[0],i[1],-h/2]])
[concat(p0,p1,p2,p3), // vertices
Unpack([for(i=[0:n-1]) let(j=(i+1)%n) [ // triangles
[i,j,j+n],[i,j+n,i+n],
[i+2
n,j+3
n,j+2
n],[i+2n,i+3n,j+3n],
[i+2
n,j+2n,j],[i+2n,j,i],
[i+3n,j+n,j+3n],[i+3*n,i+n,j+n]
]])];

function TransformPoints(p,hw,nw) = [for(i=p) WaveTransform(i,hw,nw)];

function WaveTransform(v,hw,nw) = let(x=v[0],y=v[1],z=v[2])
[x,y,z+hwsin(nwatan2(x,y))/2];

function Unpack(p) = [for(i=p) for(j=i) j];

function fa(r)=$fn>0?360/($fn>3?$fn:3):
$fe>0?$fe<r?min(45,2acos(1-$fe/r)):45:
360/max(min(360/($fa>0.01?$fa:0.01),
2
PI*r/($fs>0.01?$fs:0.01)),5);

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14991.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

The dark art of non affine transformations part III, solution to: http://forum.openscad.org/Wave-spring-tp14948.html Cheers, Trygon PS for documentation on function fa() see http://forum.openscad.org/fe-Tolerance-based-arc-approximation-tp14212.html // Trygon Dec2015 - non affine transformation: washer -> spring washer $fe=0.01; ro=10; // outside radius ri=5; // hole radius h=1; // washer thickness hw=2; // wave height nw=3; // number of waves washer=WasherObject(ro,ri,h); polyhedron(TransformPoints(washer[0],hw,nw),washer[1]); function WasherObject(ro,ri,h) = let( n=ceil(360/fa(ro)), // number of segments p0=[for(i=[0:n-1]) let(a=i*360/n) [ro*cos(a),ro*sin(a),h/2]], p1=[for(i=p0) [i[0]*ri/ro,i[1]*ri/ro,i[2]]], p2=[for(i=p0) [i[0],i[1],-h/2]], p3=[for(i=p1) [i[0],i[1],-h/2]]) [concat(p0,p1,p2,p3), // vertices Unpack([for(i=[0:n-1]) let(j=(i+1)%n) [ // triangles [i,j,j+n],[i,j+n,i+n], [i+2*n,j+3*n,j+2*n],[i+2*n,i+3*n,j+3*n], [i+2*n,j+2*n,j],[i+2*n,j,i], [i+3*n,j+n,j+3*n],[i+3*n,i+n,j+n] ]])]; function TransformPoints(p,hw,nw) = [for(i=p) WaveTransform(i,hw,nw)]; function WaveTransform(v,hw,nw) = let(x=v[0],y=v[1],z=v[2]) [x,y,z+hw*sin(nw*atan2(x,y))/2]; function Unpack(p) = [for(i=p) for(j=i) j]; function fa(r)=$fn>0?360/($fn>3?$fn:3): $fe>0?$fe<r?min(45,2*acos(1-$fe/r)):45: 360/max(min(360/($fa>0.01?$fa:0.01), 2*PI*r/($fs>0.01?$fs:0.01)),5); -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14991.html Sent from the OpenSCAD mailing list archive at Nabble.com.
T
Trygon
Sun, Dec 6, 2015 10:23 PM

Sorry, I just realised that I had the triangles inverted (points
anticlockwise rather than clockwise).  I have corrected the original post.

Thanks,
Trygon

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14996.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Sorry, I just realised that I had the triangles inverted (points anticlockwise rather than clockwise). I have corrected the original post. Thanks, Trygon -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p14996.html Sent from the OpenSCAD mailing list archive at Nabble.com.
W
wolf
Sat, Mar 19, 2016 7:53 AM

Trygon wrote

OpenSCAD currently supports a whole range of specific

linear

transformations such as translate(), rotate() and scale(), in addition to
the generic

linear

transformation multmatrix().

OpenSCAD does not provide support for non-

linear

transformations.

Both statements are false. OpenSCAD currently provides both linear
transformations (x->a+bx, with a and b constants) and non-linear
transformations (for example:  translate([sin20,cos(30),tan(10)]) is
perfectly legal, though not necessarily meaningful. Rotations are inherently
non-linear transformations, as they involve sines and cosines). Instead of
linear, Trygon should have used the term affine to describe current
OpenSCAD's capabilities.
But doing so has consequences: Since one of the properties of an affine
transformation is that straight lines are transformed into other straight
lines, this implies that as long as OpenSCAD wants to output .stl files, it
cannot support non-affine transformations.
After all, a .stl file is nothing but a [structured] list of vertices, which
are connected by straight lines, and not curved ones as is inevitable for
non-affine transformations.

BTW, doug.moen's algorithm does not have any value either. This is because
when, say, a square is subjected to an affine transformation, it must remain
a quadrangle (i.e. its vertex count remains unchanged), and it must remain
flat. That is part and parcel of an affine transformation. Thus there is no
need to create extra vertices.

Finally, the outcome of the multiplication of one or several vector(s) with
a matrix (that is what multmatrix() is) need not be restricted to affine
transformations. Some OpenSCAD shapes allow a twist parameter - the
restriction arises out of the need to produce .stl files. Twist is the
implemented as a succession of skew transformations.

wolf

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p16578.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

Trygon wrote > OpenSCAD currently supports a whole range of specific * > linear * > transformations such as translate(), rotate() and scale(), in addition to > the generic * > linear * > transformation multmatrix(). > > OpenSCAD does not provide support for non- * > linear * > transformations. Both statements are false. OpenSCAD currently provides both linear transformations (x->a+bx, with a and b constants) and non-linear transformations (for example: translate([sin20,cos(30),tan(10)]) is perfectly legal, though not necessarily meaningful. Rotations are inherently non-linear transformations, as they involve sines and cosines). Instead of *linear*, Trygon should have used the term *affine* to describe current OpenSCAD's capabilities. But doing so has consequences: Since one of the properties of an affine transformation is that straight lines are transformed into other straight lines, this implies that as long as OpenSCAD wants to output .stl files, it cannot support non-affine transformations. After all, a .stl file is nothing but a [structured] list of vertices, which are connected by straight lines, and not curved ones as is inevitable for non-affine transformations. BTW, doug.moen's algorithm does not have any value either. This is because when, say, a square is subjected to an affine transformation, it must remain a quadrangle (i.e. its vertex count remains unchanged), and it must remain flat. That is part and parcel of an affine transformation. Thus there is no need to create extra vertices. Finally, the outcome of the multiplication of one or several vector(s) with a matrix (that is what multmatrix() is) need not be restricted to affine transformations. Some OpenSCAD shapes allow a twist parameter - the restriction arises out of the need to produce .stl files. Twist is the implemented as a succession of skew transformations. wolf -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p16578.html Sent from the OpenSCAD mailing list archive at Nabble.com.
CA
Carsten Arnholm
Sat, Mar 19, 2016 9:41 AM

On 19. mars 2016 08:53, wolf wrote:

After all, a .stl file is nothing but a [structured] list of vertices, which
are connected by straight lines,

This is somewhat misleading. STL files do not contain a lists of
vertices. STL files contain only a set of topologically disconnected
triangles with coordinates duplicated locally in every triangle. Every
would-be vertex has to be mentioned at least 3 times. This is one of the
reasons why why STL is an unfortunate standard.

Your description applies better to an AMF file or generally a polyhedron
mesh with a structured vector of vertices and where faces are defined
via indices into the vertex vector. This is much better as it removes
the possibility of ambiguities.

Finally, the outcome of the multiplication of one or several vector(s) with
a matrix (that is what multmatrix() is) need not be restricted to affine
transformations.

Every transformation in OpenSCAD and most similar systems is eventually
expressed a 4x4 homogeneous coordinate transformation matrix,
multmatrix() is just the explicit form of that in OpenSCAD. Although
such matrices can express things like perspective, in CAD geometry it is
most commonly used to express just translation, scaling, mirroring and
rotation. Straight lines are preserved for these, but the curvature of
arcs can be affected by scaling.

Carsten Arnholm

On 19. mars 2016 08:53, wolf wrote: > After all, a .stl file is nothing but a [structured] list of vertices, which > are connected by straight lines, This is somewhat misleading. STL files do not contain a lists of vertices. STL files contain only a set of topologically disconnected triangles with coordinates duplicated locally in every triangle. Every would-be vertex has to be mentioned at least 3 times. This is one of the reasons why why STL is an unfortunate standard. Your description applies better to an AMF file or generally a polyhedron mesh with a structured vector of vertices and where faces are defined via indices into the vertex vector. This is much better as it removes the possibility of ambiguities. > Finally, the outcome of the multiplication of one or several vector(s) with > a matrix (that is what multmatrix() is) need not be restricted to affine > transformations. Every transformation in OpenSCAD and most similar systems is eventually expressed a 4x4 homogeneous coordinate transformation matrix, multmatrix() is just the explicit form of that in OpenSCAD. Although such matrices can express things like perspective, in CAD geometry it is most commonly used to express just translation, scaling, mirroring and rotation. Straight lines are preserved for these, but the curvature of arcs can be affected by scaling. Carsten Arnholm
DM
doug moen
Sat, Mar 19, 2016 3:46 PM

OpenSCAD supports affine transformations via multmatrix, but it does not
support the more general class of projective transformations (which
includes the perspective transformation), even though these can also be
represented by 4x4 matrixes.

I've looked at a number of solid modelling languages, in addition to
OpenSCAD, and the only one I've found that supports generalized projective
transformations is SGDL. SGDL is based on projective geometry, which is a
generalization of Euclidean geometry that includes points at infinity. In
SGDL, 3-space coordinates are always represented as homogenous coordinates:
[x,y,z,w], where the point is at infinity if w==0. SGDL also supports
infinitely large solids.

I'm not an expert on projective geometry, but I think the problem with
supporting general projective transformations in a Euclidean geometry
system like OpenSCAD is just that a projective transformation can map a
vertex to a point at infinity, and we have no way to deal with that in our
representation.

Does anybody on the list have a better understanding of this? What are all
the things that would go wrong if we tried to extend multmatrix to support
projective transformations?

On 19 March 2016 at 03:53, wolf wv99999@gmail.com wrote:

Trygon wrote

OpenSCAD currently supports a whole range of specific

linear

transformations such as translate(), rotate() and scale(), in addition

to

the generic

linear

transformation multmatrix().

OpenSCAD does not provide support for non-

linear

transformations.

Both statements are false. OpenSCAD currently provides both linear
transformations (x->a+bx, with a and b constants) and non-linear
transformations (for example:  translate([sin20,cos(30),tan(10)]) is
perfectly legal, though not necessarily meaningful. Rotations are
inherently
non-linear transformations, as they involve sines and cosines). Instead of
linear, Trygon should have used the term affine to describe current
OpenSCAD's capabilities.
But doing so has consequences: Since one of the properties of an affine
transformation is that straight lines are transformed into other straight
lines, this implies that as long as OpenSCAD wants to output .stl files, it
cannot support non-affine transformations.
After all, a .stl file is nothing but a [structured] list of vertices,
which
are connected by straight lines, and not curved ones as is inevitable for
non-affine transformations.

BTW, doug.moen's algorithm does not have any value either. This is because
when, say, a square is subjected to an affine transformation, it must
remain
a quadrangle (i.e. its vertex count remains unchanged), and it must remain
flat. That is part and parcel of an affine transformation. Thus there is no
need to create extra vertices.

Finally, the outcome of the multiplication of one or several vector(s) with
a matrix (that is what multmatrix() is) need not be restricted to affine
transformations. Some OpenSCAD shapes allow a twist parameter - the
restriction arises out of the need to produce .stl files. Twist is the
implemented as a succession of skew transformations.

wolf

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p16578.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

OpenSCAD supports affine transformations via multmatrix, but it does not support the more general class of projective transformations (which includes the perspective transformation), even though these can also be represented by 4x4 matrixes. I've looked at a number of solid modelling languages, in addition to OpenSCAD, and the only one I've found that supports generalized projective transformations is SGDL. SGDL is based on projective geometry, which is a generalization of Euclidean geometry that includes points at infinity. In SGDL, 3-space coordinates are always represented as homogenous coordinates: [x,y,z,w], where the point is at infinity if w==0. SGDL also supports infinitely large solids. I'm not an expert on projective geometry, but I think the problem with supporting general projective transformations in a Euclidean geometry system like OpenSCAD is just that a projective transformation can map a vertex to a point at infinity, and we have no way to deal with that in our representation. Does anybody on the list have a better understanding of this? What are all the things that would go wrong if we tried to extend multmatrix to support projective transformations? On 19 March 2016 at 03:53, wolf <wv99999@gmail.com> wrote: > Trygon wrote > > OpenSCAD currently supports a whole range of specific > * > > linear > * > > transformations such as translate(), rotate() and scale(), in addition > to > > the generic > * > > linear > * > > transformation multmatrix(). > > > > OpenSCAD does not provide support for non- > * > > linear > * > > transformations. > > Both statements are false. OpenSCAD currently provides both linear > transformations (x->a+bx, with a and b constants) and non-linear > transformations (for example: translate([sin20,cos(30),tan(10)]) is > perfectly legal, though not necessarily meaningful. Rotations are > inherently > non-linear transformations, as they involve sines and cosines). Instead of > *linear*, Trygon should have used the term *affine* to describe current > OpenSCAD's capabilities. > But doing so has consequences: Since one of the properties of an affine > transformation is that straight lines are transformed into other straight > lines, this implies that as long as OpenSCAD wants to output .stl files, it > cannot support non-affine transformations. > After all, a .stl file is nothing but a [structured] list of vertices, > which > are connected by straight lines, and not curved ones as is inevitable for > non-affine transformations. > > BTW, doug.moen's algorithm does not have any value either. This is because > when, say, a square is subjected to an affine transformation, it must > remain > a quadrangle (i.e. its vertex count remains unchanged), and it must remain > flat. That is part and parcel of an affine transformation. Thus there is no > need to create extra vertices. > > Finally, the outcome of the multiplication of one or several vector(s) with > a matrix (that is what multmatrix() is) need not be restricted to affine > transformations. Some OpenSCAD shapes allow a twist parameter - the > restriction arises out of the need to produce .stl files. Twist is the > implemented as a succession of skew transformations. > > wolf > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p16578.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
RW
Rogier Wolff
Sat, Mar 19, 2016 6:00 PM

On Sat, Mar 19, 2016 at 11:46:10AM -0400, doug moen wrote:

OpenSCAD supports affine transformations via multmatrix, but it does not
support the more general class of projective transformations (which
includes the perspective transformation), even though these can also be
represented by 4x4 matrixes.

I've looked at a number of solid modelling languages, in addition to
OpenSCAD, and the only one I've found that supports generalized projective
transformations is SGDL. SGDL is based on projective geometry, which is a
generalization of Euclidean geometry that includes points at infinity. In
SGDL, 3-space coordinates are always represented as homogenous coordinates:
[x,y,z,w], where the point is at infinity if w==0. SGDL also supports
infinitely large solids.

I took "computer graphics" at caltech from Prof. Jim Blinn in 1985....
He is a big proponent of this way of working.

Points in three-space are represented by [x, y, z, 1]. A projection
(in 4-space) towards the origin on the w=1 plane (ehh solid) happens
when you divide by w to "come back to 3-space". This also means you
can do 3D->2D projections.

Because you start with w=1, you have a constant that you can add to
xyz, to perform translations.

Everything is linear, so for example a rotation followed by a
translation can be done in one step by multiplying their matrices.

How all this applies to openscad, I don't know. I have too little
familiarity with the openscad internals.

Roger. 

--
** R.E.Wolff@BitWizard.nl ** http://www.BitWizard.nl/ ** +31-15-2600998 **
**    Delftechpark 26 2628 XH  Delft, The Netherlands. KVK: 27239233    **
-- BitWizard writes Linux device drivers for any device you may have! --
The plan was simple, like my brother-in-law Phil. But unlike
Phil, this plan just might work.

On Sat, Mar 19, 2016 at 11:46:10AM -0400, doug moen wrote: > OpenSCAD supports affine transformations via multmatrix, but it does not > support the more general class of projective transformations (which > includes the perspective transformation), even though these can also be > represented by 4x4 matrixes. > > I've looked at a number of solid modelling languages, in addition to > OpenSCAD, and the only one I've found that supports generalized projective > transformations is SGDL. SGDL is based on projective geometry, which is a > generalization of Euclidean geometry that includes points at infinity. In > SGDL, 3-space coordinates are always represented as homogenous coordinates: > [x,y,z,w], where the point is at infinity if w==0. SGDL also supports > infinitely large solids. I took "computer graphics" at caltech from Prof. Jim Blinn in 1985.... He is a big proponent of this way of working. Points in three-space are represented by [x, y, z, 1]. A projection (in 4-space) towards the origin on the w=1 plane (ehh solid) happens when you divide by w to "come back to 3-space". This also means you can do 3D->2D projections. Because you start with w=1, you have a constant that you can add to xyz, to perform translations. Everything is linear, so for example a rotation followed by a translation can be done in one step by multiplying their matrices. How all this applies to openscad, I don't know. I have too little familiarity with the openscad internals. Roger. -- ** R.E.Wolff@BitWizard.nl ** http://www.BitWizard.nl/ ** +31-15-2600998 ** ** Delftechpark 26 2628 XH Delft, The Netherlands. KVK: 27239233 ** *-- BitWizard writes Linux device drivers for any device you may have! --* The plan was simple, like my brother-in-law Phil. But unlike Phil, this plan just might work.
W
wolf
Sun, Mar 20, 2016 2:22 AM

When I researched, and made, my previous comment, I allowed myself to be
guided by conservation laws. Conservation laws are very powerful constructs,
as they tell you what you need not to bother with when planning a change,
and as such reduce the complexity of your task. They also permit you to
freely change the direction of your reasoning, going about designing first
the roof of your house or the foundations, or even the place where the
computer sits on which you do OpenSCAD. The result will always be the same,
but the traps you fall into when you do your planning will differ.
OpenSCAD's output is not a value in itself, but rather a tool to access the
capabilities of other tools, such as a 3D printer or a laser cutter. Thus,
it makes sense to start from the end, from the limitations that a .stl file
output places on OpenSCAD's internals.
If you open up the .stl of cube([1,1,1]) in a text editor, you get, after
the removal of some spaces and <newlines> (and sorting on the facet normal,
just to make the internal structure clearer), this table:

solid OpenSCAD_Model
facet normal -1 0 0  outer  loop  vertex  0 1 1  vertex 0 0 0  vertex
0 0 0  endloop  endfacet
facet normal -1 0 0  outer  loop  vertex  0 0 0  vertex 0 1 1  vertex
0 1 1  endloop  endfacet
facet normal 0 -1 0  outer  loop  vertex  1 0 1  vertex 0 0 0  vertex
0 0 0  endloop  endfacet
facet normal 0 -1 0  outer  loop  vertex  0 0 0  vertex 1 0 1  vertex
1 0 1  endloop  endfacet
facet normal 0 0 -1  outer  loop  vertex  1 1 0  vertex 0 0 0  vertex
0 0 0  endloop  endfacet
facet normal 0 0 -1  outer  loop  vertex  0 0 0  vertex 1 1 0  vertex
1 1 0  endloop  endfacet
facet normal 0 0 1    outer  loop  vertex  1 0 1  vertex 0 1 1  vertex
0 1 1  endloop  endfacet
facet normal 0 0 1    outer  loop  vertex  0 1 1  vertex 1 0 1  vertex
1 0 1  endloop  endfacet
facet normal 0 1 0    outer  loop  vertex  1 1 0  vertex 0 1 1  vertex
0 1 1  endloop  endfacet
facet normal 0 1 0    outer  loop  vertex  0 1 1  vertex 1 1 0  vertex
1 1 0  endloop  endfacet
facet normal 1 0 0    outer  loop  vertex  1 1 0  vertex 1 0 1  vertex
1 0 1  endloop  endfacet
facet normal 1 0 0    outer  loop  vertex  1 0 1  vertex 1 1 0  vertex
1 1 0  endloop  endfacet
endsolid OpenSCAD_Model

Unlike what Wikipedia  https://en.wikipedia.org/wiki/STL_%28file_format%29
makes me expect, there are twice as many facets listed as a cube has faces,
and each facet points only to two vertices. I haven't investigated so far
whether this is due to an OpenSCAD bug or inappropriate Wikipedia
information.

As to the question on the usefulness of projective geometry extensions to
OpenSCAD, I fail to see the usefulness of it. Yes, the display looks nicer,
and you can easily program tapers, but how often is that used? So my vote is
against it, as is my vote against extensions to multmatrix(). Here I would
rather follow the philosophy projected with OpenSCAD2: simpler is better,
and deprecate multmatrix(), because it requires so much background in
mathematics to use it effectively. The useful portions of multmatrix() have
already been extracted into other transformations, as this program segment
shows:

TranslatMatrix= [ [1, 0, 0, 10],
[0, 1, 0, 20],
[0, 0, 1, 30],
[0, 0, 0,  1]
];
ScaleMatrix=    [ [1, 0, 0, 0],
[0, 1/2, 0, 0],
[0, 0, 1/3, 0],
[0, 0, 0,  1]
];
Rotate_Around_X=[ [1, 0, 0, 0],                //source:
https://en.wikipedia.org/wiki/Rotation_formalisms_in_three_dimensions
[0, cos(30), -sin(30), 0],
[0, sin(30), cos(30), 0],
[0, 0, 0, 1]
];
Rotate_Around_Y=[ [cos(30), 0, sin(30), 0],
[ 0, 1, 0, 0],
[-sin(30), 0,cos(30), 0],
[0, 0, 0, 1]
];
Rotate_Around_Z=[ [cos(30), -sin(30), 0, 0],
[sin(30), cos(30), 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]
];
//SkewMatrix=    // source:
https://en.wikipedia.org/wiki/Rotation_matrix#Skew_parameters_via_Cayley.27s_formula
//  https://en.wikipedia.org/wiki/Cayley_transform
//  https://en.wikipedia.org/wiki/Skew-symmetric_matrix

//T_Simple();
//T_mult();
//S_Simple();
//S_mult();
//R_X_Simple();
//R_X_mult();
//R_Y_mult();
R_Z_mult();

module T_Simple()    //this is one way of doing a translation
translate([10,20,30])
cube([10,20,30]);
module T_mult()    //this is another way of doing the same translation
multmatrix(m = TranslatMatrix)
cube([10,20,1/3]);
module S_Simple()    //this is one way of doing scaling
scale([1,1/2,1/3])
cube([10,20,30]);
module S_mult()    //this is another way of doing the same scaling
multmatrix(m = ScaleMatrix)
cube([10,20,30]);
module R_X_Simple()    //this is one way of doing a rotation around the x
axis
rotate(30,[1,0,0])
cube([10,20,30]);
module R_X_mult()    //this is another way of doing the same rotation around
the x axis
multmatrix(m = Rotate_Around_X)
cube([10,20,30]);
module R_Y_mult()    //this is a rotation around the y axis
multmatrix(m = Rotate_Around_Y)
cube([10,20,30]);
module R_Z_mult()    //this is a rotation around the z axis
multmatrix(m = Rotate_Around_Z)
cube([10,20,30]);

As far as I know, skew or shear transformations currently require the use of
multmatrix(), but then who uses them?
Because Marius Kintel asked for them, I outline here another transformation:
offset.

$fn=50;
Diameter=2;      // diameter of sphere from which ellipsoid is created
Offset=0.1Diameter;
MaxDim=[3
Diameter,1Diameter,.5Diameter];    // long axes of ellipsoid

MakeOffset();
MakeCutout();
TestPosition();

module MakeOffset()
scale([1-2Offset/MaxDim[0],1-2Offset/MaxDim[1],1-2*Offset/MaxDim[2]])
// for a true offset, MaxDim[...] needs to be replaced with the norm of each
vertex for the ellipsoid
Ellipsoid();
module TestPosition()
translate([MaxDim[0]/2-Offset/2,0,0])    sphere(d=Offset);
translate([0,-(MaxDim[1]/2-Offset/2),0])  sphere(d=Offset);
translate([0,0,MaxDim[2]/2-Offset/2])    sphere(d=Offset);
module MakeCutout()
difference()
{ Ellipsoid();
translate([0,-15,15])  cube([70,30,30], center=true);
}
module Ellipsoid()
scale([MaxDim[0]/Diameter,MaxDim[1]/Diameter,MaxDim[2]/Diameter])
sphere(d=Diameter);

It doesn't quite work in userspace, but comes pretty close. One line, as
commented, needs access to the vertex vectors, which OpenSCAD does not
readily provide. Work for someone with knowledge of the internals.
http://forum.openscad.org/file/n16588/Offset.jpg
The yellow color in the cutout indicates a problem OpenSCAD has with the
faces created by module MakeCutout(). Probably inside-out faces. They were
made with version 2015.03-1.

wolf

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p16588.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

When I researched, and made, my previous comment, I allowed myself to be guided by conservation laws. Conservation laws are very powerful constructs, as they tell you what you need not to bother with when planning a change, and as such reduce the complexity of your task. They also permit you to freely change the direction of your reasoning, going about designing first the roof of your house or the foundations, or even the place where the computer sits on which you do OpenSCAD. The result will always be the same, but the traps you fall into when you do your planning will differ. OpenSCAD's output is not a value in itself, but rather a tool to access the capabilities of other tools, such as a 3D printer or a laser cutter. Thus, it makes sense to start from the end, from the limitations that a .stl file output places on OpenSCAD's internals. If you open up the .stl of cube([1,1,1]) in a text editor, you get, after the removal of some spaces and <newlines> (and sorting on the facet normal, just to make the internal structure clearer), this table: solid OpenSCAD_Model facet normal -1 0 0 outer loop vertex 0 1 1 vertex 0 0 0 vertex 0 0 0 endloop endfacet facet normal -1 0 0 outer loop vertex 0 0 0 vertex 0 1 1 vertex 0 1 1 endloop endfacet facet normal 0 -1 0 outer loop vertex 1 0 1 vertex 0 0 0 vertex 0 0 0 endloop endfacet facet normal 0 -1 0 outer loop vertex 0 0 0 vertex 1 0 1 vertex 1 0 1 endloop endfacet facet normal 0 0 -1 outer loop vertex 1 1 0 vertex 0 0 0 vertex 0 0 0 endloop endfacet facet normal 0 0 -1 outer loop vertex 0 0 0 vertex 1 1 0 vertex 1 1 0 endloop endfacet facet normal 0 0 1 outer loop vertex 1 0 1 vertex 0 1 1 vertex 0 1 1 endloop endfacet facet normal 0 0 1 outer loop vertex 0 1 1 vertex 1 0 1 vertex 1 0 1 endloop endfacet facet normal 0 1 0 outer loop vertex 1 1 0 vertex 0 1 1 vertex 0 1 1 endloop endfacet facet normal 0 1 0 outer loop vertex 0 1 1 vertex 1 1 0 vertex 1 1 0 endloop endfacet facet normal 1 0 0 outer loop vertex 1 1 0 vertex 1 0 1 vertex 1 0 1 endloop endfacet facet normal 1 0 0 outer loop vertex 1 0 1 vertex 1 1 0 vertex 1 1 0 endloop endfacet endsolid OpenSCAD_Model Unlike what Wikipedia https://en.wikipedia.org/wiki/STL_%28file_format%29 makes me expect, there are twice as many facets listed as a cube has faces, and each facet points only to two vertices. I haven't investigated so far whether this is due to an OpenSCAD bug or inappropriate Wikipedia information. As to the question on the usefulness of projective geometry extensions to OpenSCAD, I fail to see the usefulness of it. Yes, the display looks nicer, and you can easily program tapers, but how often is that used? So my vote is against it, as is my vote against extensions to multmatrix(). Here I would rather follow the philosophy projected with OpenSCAD2: simpler is better, and deprecate multmatrix(), because it requires so much background in mathematics to use it effectively. The useful portions of multmatrix() have already been extracted into other transformations, as this program segment shows: TranslatMatrix= [ [1, 0, 0, 10], [0, 1, 0, 20], [0, 0, 1, 30], [0, 0, 0, 1] ]; ScaleMatrix= [ [1, 0, 0, 0], [0, 1/2, 0, 0], [0, 0, 1/3, 0], [0, 0, 0, 1] ]; Rotate_Around_X=[ [1, 0, 0, 0], //source: https://en.wikipedia.org/wiki/Rotation_formalisms_in_three_dimensions [0, cos(30), -sin(30), 0], [0, sin(30), cos(30), 0], [0, 0, 0, 1] ]; Rotate_Around_Y=[ [cos(30), 0, sin(30), 0], [ 0, 1, 0, 0], [-sin(30), 0,cos(30), 0], [0, 0, 0, 1] ]; Rotate_Around_Z=[ [cos(30), -sin(30), 0, 0], [sin(30), cos(30), 0, 0], [0, 0, 1, 0], [0, 0, 0, 1] ]; //SkewMatrix= // source: https://en.wikipedia.org/wiki/Rotation_matrix#Skew_parameters_via_Cayley.27s_formula // https://en.wikipedia.org/wiki/Cayley_transform // https://en.wikipedia.org/wiki/Skew-symmetric_matrix //T_Simple(); //T_mult(); //S_Simple(); //S_mult(); //R_X_Simple(); //R_X_mult(); //R_Y_mult(); R_Z_mult(); module T_Simple() //this is one way of doing a translation translate([10,20,30]) cube([10,20,30]); module T_mult() //this is another way of doing the same translation multmatrix(m = TranslatMatrix) cube([10,20,1/3]); module S_Simple() //this is one way of doing scaling scale([1,1/2,1/3]) cube([10,20,30]); module S_mult() //this is another way of doing the same scaling multmatrix(m = ScaleMatrix) cube([10,20,30]); module R_X_Simple() //this is one way of doing a rotation around the x axis rotate(30,[1,0,0]) cube([10,20,30]); module R_X_mult() //this is another way of doing the same rotation around the x axis multmatrix(m = Rotate_Around_X) cube([10,20,30]); module R_Y_mult() //this is a rotation around the y axis multmatrix(m = Rotate_Around_Y) cube([10,20,30]); module R_Z_mult() //this is a rotation around the z axis multmatrix(m = Rotate_Around_Z) cube([10,20,30]); As far as I know, skew or shear transformations currently require the use of multmatrix(), but then who uses them? Because Marius Kintel asked for them, I outline here another transformation: offset. $fn=50; Diameter=2; // diameter of sphere from which ellipsoid is created Offset=0.1*Diameter; MaxDim=[3*Diameter,1*Diameter,.5*Diameter]; // long axes of ellipsoid MakeOffset(); MakeCutout(); TestPosition(); module MakeOffset() scale([1-2*Offset/MaxDim[0],1-2*Offset/MaxDim[1],1-2*Offset/MaxDim[2]]) // for a true offset, MaxDim[...] needs to be replaced with the norm of each vertex for the ellipsoid Ellipsoid(); module TestPosition() translate([MaxDim[0]/2-Offset/2,0,0]) sphere(d=Offset); translate([0,-(MaxDim[1]/2-Offset/2),0]) sphere(d=Offset); translate([0,0,MaxDim[2]/2-Offset/2]) sphere(d=Offset); module MakeCutout() difference() { Ellipsoid(); translate([0,-15,15]) cube([70,30,30], center=true); } module Ellipsoid() scale([MaxDim[0]/Diameter,MaxDim[1]/Diameter,MaxDim[2]/Diameter]) sphere(d=Diameter); It doesn't quite work in userspace, but comes pretty close. One line, as commented, needs access to the vertex vectors, which OpenSCAD does not readily provide. Work for someone with knowledge of the internals. <http://forum.openscad.org/file/n16588/Offset.jpg> The yellow color in the cutout indicates a problem OpenSCAD has with the faces created by module MakeCutout(). Probably inside-out faces. They were made with version 2015.03-1. wolf -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p16588.html Sent from the OpenSCAD mailing list archive at Nabble.com.
DM
doug moen
Sun, Mar 20, 2016 3:42 AM

Wolf said: "Unlike what Wikipedia
https://en.wikipedia.org/wiki/STL_%28file_format%29
makes me expect, there are twice as many facets listed as a cube has faces,
and each facet points only to two vertices. I haven't investigated so far
whether this is due to an OpenSCAD bug or inappropriate Wikipedia
information."

The Wikipedia article is correct and this is not an OpenSCAD bug. An STL
file contains a list of triangles, each of which has 3 vertices. A cube has
6 square faces, and each square must be split into 2 triangles in order to
be represented by STL. So that's 6 * 2 = 12 triangles.

The wikipedia article addresses your point of confusing by stating this:"The
structure of the format suggests that other possibilities exist (e.g.,
facets with more than one "loop", or loops with more than three vertices).
In practice, however, all facets are simple triangles."

On 19 March 2016 at 22:22, wolf wv99999@gmail.com wrote:

When I researched, and made, my previous comment, I allowed myself to be
guided by conservation laws. Conservation laws are very powerful
constructs,
as they tell you what you need not to bother with when planning a change,
and as such reduce the complexity of your task. They also permit you to
freely change the direction of your reasoning, going about designing first
the roof of your house or the foundations, or even the place where the
computer sits on which you do OpenSCAD. The result will always be the same,
but the traps you fall into when you do your planning will differ.
OpenSCAD's output is not a value in itself, but rather a tool to access the
capabilities of other tools, such as a 3D printer or a laser cutter. Thus,
it makes sense to start from the end, from the limitations that a .stl file
output places on OpenSCAD's internals.
If you open up the .stl of cube([1,1,1]) in a text editor, you get, after
the removal of some spaces and <newlines> (and sorting on the facet normal,
just to make the internal structure clearer), this table:

solid OpenSCAD_Model
facet normal -1 0 0  outer  loop  vertex  0 1 1  vertex 0 0 0  vertex
0 0 0  endloop  endfacet
facet normal -1 0 0  outer  loop  vertex  0 0 0  vertex 0 1 1  vertex
0 1 1  endloop  endfacet
facet normal 0 -1 0  outer  loop  vertex  1 0 1  vertex 0 0 0  vertex
0 0 0  endloop  endfacet
facet normal 0 -1 0  outer  loop  vertex  0 0 0  vertex 1 0 1  vertex
1 0 1  endloop  endfacet
facet normal 0 0 -1  outer  loop  vertex  1 1 0  vertex 0 0 0  vertex
0 0 0  endloop  endfacet
facet normal 0 0 -1  outer  loop  vertex  0 0 0  vertex 1 1 0  vertex
1 1 0  endloop  endfacet
facet normal 0 0 1    outer  loop  vertex  1 0 1  vertex 0 1 1  vertex
0 1 1  endloop  endfacet
facet normal 0 0 1    outer  loop  vertex  0 1 1  vertex 1 0 1  vertex
1 0 1  endloop  endfacet
facet normal 0 1 0    outer  loop  vertex  1 1 0  vertex 0 1 1  vertex
0 1 1  endloop  endfacet
facet normal 0 1 0    outer  loop  vertex  0 1 1  vertex 1 1 0  vertex
1 1 0  endloop  endfacet
facet normal 1 0 0    outer  loop  vertex  1 1 0  vertex 1 0 1  vertex
1 0 1  endloop  endfacet
facet normal 1 0 0    outer  loop  vertex  1 0 1  vertex 1 1 0  vertex
1 1 0  endloop  endfacet
endsolid OpenSCAD_Model

Unlike what Wikipedia  https://en.wikipedia.org/wiki/STL_%28file_format%29
makes me expect, there are twice as many facets listed as a cube has faces,
and each facet points only to two vertices. I haven't investigated so far
whether this is due to an OpenSCAD bug or inappropriate Wikipedia
information.

As to the question on the usefulness of projective geometry extensions to
OpenSCAD, I fail to see the usefulness of it. Yes, the display looks nicer,
and you can easily program tapers, but how often is that used? So my vote
is
against it, as is my vote against extensions to multmatrix(). Here I would
rather follow the philosophy projected with OpenSCAD2: simpler is better,
and deprecate multmatrix(), because it requires so much background in
mathematics to use it effectively. The useful portions of multmatrix() have
already been extracted into other transformations, as this program segment
shows:

TranslatMatrix= [ [1, 0, 0, 10],
[0, 1, 0, 20],
[0, 0, 1, 30],
[0, 0, 0,  1]
];
ScaleMatrix=    [ [1, 0, 0, 0],
[0, 1/2, 0, 0],
[0, 0, 1/3, 0],
[0, 0, 0,  1]
];
Rotate_Around_X=[ [1, 0, 0, 0],                //source:
https://en.wikipedia.org/wiki/Rotation_formalisms_in_three_dimensions
[0, cos(30), -sin(30), 0],
[0, sin(30), cos(30), 0],
[0, 0, 0, 1]
];
Rotate_Around_Y=[ [cos(30), 0, sin(30), 0],
[ 0, 1, 0, 0],
[-sin(30), 0,cos(30), 0],
[0, 0, 0, 1]
];
Rotate_Around_Z=[ [cos(30), -sin(30), 0, 0],
[sin(30), cos(30), 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]
];
//SkewMatrix=    // source:

https://en.wikipedia.org/wiki/Rotation_matrix#Skew_parameters_via_Cayley.27s_formula
//  https://en.wikipedia.org/wiki/Cayley_transform
//  https://en.wikipedia.org/wiki/Skew-symmetric_matrix

//T_Simple();
//T_mult();
//S_Simple();
//S_mult();
//R_X_Simple();
//R_X_mult();
//R_Y_mult();
R_Z_mult();

module T_Simple()    //this is one way of doing a translation
translate([10,20,30])
cube([10,20,30]);
module T_mult()    //this is another way of doing the same translation
multmatrix(m = TranslatMatrix)
cube([10,20,1/3]);
module S_Simple()    //this is one way of doing scaling
scale([1,1/2,1/3])
cube([10,20,30]);
module S_mult()    //this is another way of doing the same scaling
multmatrix(m = ScaleMatrix)
cube([10,20,30]);
module R_X_Simple()    //this is one way of doing a rotation around the x
axis
rotate(30,[1,0,0])
cube([10,20,30]);
module R_X_mult()    //this is another way of doing the same rotation
around
the x axis
multmatrix(m = Rotate_Around_X)
cube([10,20,30]);
module R_Y_mult()    //this is a rotation around the y axis
multmatrix(m = Rotate_Around_Y)
cube([10,20,30]);
module R_Z_mult()    //this is a rotation around the z axis
multmatrix(m = Rotate_Around_Z)
cube([10,20,30]);

As far as I know, skew or shear transformations currently require the use
of
multmatrix(), but then who uses them?
Because Marius Kintel asked for them, I outline here another
transformation:
offset.

$fn=50;
Diameter=2;      // diameter of sphere from which ellipsoid is created
Offset=0.1Diameter;
MaxDim=[3
Diameter,1Diameter,.5Diameter];    // long axes of ellipsoid

MakeOffset();
MakeCutout();
TestPosition();

module MakeOffset()
scale([1-2Offset/MaxDim[0],1-2Offset/MaxDim[1],1-2*Offset/MaxDim[2]])
// for a true offset, MaxDim[...] needs to be replaced with the norm of
each
vertex for the ellipsoid
Ellipsoid();
module TestPosition()
translate([MaxDim[0]/2-Offset/2,0,0])    sphere(d=Offset);
translate([0,-(MaxDim[1]/2-Offset/2),0])  sphere(d=Offset);
translate([0,0,MaxDim[2]/2-Offset/2])    sphere(d=Offset);
module MakeCutout()
difference()
{ Ellipsoid();
translate([0,-15,15])  cube([70,30,30], center=true);
}
module Ellipsoid()
scale([MaxDim[0]/Diameter,MaxDim[1]/Diameter,MaxDim[2]/Diameter])
sphere(d=Diameter);

It doesn't quite work in userspace, but comes pretty close. One line, as
commented, needs access to the vertex vectors, which OpenSCAD does not
readily provide. Work for someone with knowledge of the internals.
http://forum.openscad.org/file/n16588/Offset.jpg
The yellow color in the cutout indicates a problem OpenSCAD has with the
faces created by module MakeCutout(). Probably inside-out faces. They were
made with version 2015.03-1.

wolf

--
View this message in context:
http://forum.openscad.org/Non-Linear-Transformations-tp14539p16588.html
Sent from the OpenSCAD mailing list archive at Nabble.com.


OpenSCAD mailing list
Discuss@lists.openscad.org
http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org

Wolf said: "Unlike what Wikipedia https://en.wikipedia.org/wiki/STL_%28file_format%29 makes me expect, there are twice as many facets listed as a cube has faces, and each facet points only to two vertices. I haven't investigated so far whether this is due to an OpenSCAD bug or inappropriate Wikipedia information." The Wikipedia article is correct and this is not an OpenSCAD bug. An STL file contains a list of triangles, each of which has 3 vertices. A cube has 6 square faces, and each square must be split into 2 triangles in order to be represented by STL. So that's 6 * 2 = 12 triangles. The wikipedia article addresses your point of confusing by stating this:"The structure of the format suggests that other possibilities exist (e.g., facets with more than one "loop", or loops with more than three vertices). In practice, however, all facets are simple triangles." On 19 March 2016 at 22:22, wolf <wv99999@gmail.com> wrote: > When I researched, and made, my previous comment, I allowed myself to be > guided by conservation laws. Conservation laws are very powerful > constructs, > as they tell you what you need not to bother with when planning a change, > and as such reduce the complexity of your task. They also permit you to > freely change the direction of your reasoning, going about designing first > the roof of your house or the foundations, or even the place where the > computer sits on which you do OpenSCAD. The result will always be the same, > but the traps you fall into when you do your planning will differ. > OpenSCAD's output is not a value in itself, but rather a tool to access the > capabilities of other tools, such as a 3D printer or a laser cutter. Thus, > it makes sense to start from the end, from the limitations that a .stl file > output places on OpenSCAD's internals. > If you open up the .stl of cube([1,1,1]) in a text editor, you get, after > the removal of some spaces and <newlines> (and sorting on the facet normal, > just to make the internal structure clearer), this table: > > solid OpenSCAD_Model > facet normal -1 0 0 outer loop vertex 0 1 1 vertex 0 0 0 vertex > 0 0 0 endloop endfacet > facet normal -1 0 0 outer loop vertex 0 0 0 vertex 0 1 1 vertex > 0 1 1 endloop endfacet > facet normal 0 -1 0 outer loop vertex 1 0 1 vertex 0 0 0 vertex > 0 0 0 endloop endfacet > facet normal 0 -1 0 outer loop vertex 0 0 0 vertex 1 0 1 vertex > 1 0 1 endloop endfacet > facet normal 0 0 -1 outer loop vertex 1 1 0 vertex 0 0 0 vertex > 0 0 0 endloop endfacet > facet normal 0 0 -1 outer loop vertex 0 0 0 vertex 1 1 0 vertex > 1 1 0 endloop endfacet > facet normal 0 0 1 outer loop vertex 1 0 1 vertex 0 1 1 vertex > 0 1 1 endloop endfacet > facet normal 0 0 1 outer loop vertex 0 1 1 vertex 1 0 1 vertex > 1 0 1 endloop endfacet > facet normal 0 1 0 outer loop vertex 1 1 0 vertex 0 1 1 vertex > 0 1 1 endloop endfacet > facet normal 0 1 0 outer loop vertex 0 1 1 vertex 1 1 0 vertex > 1 1 0 endloop endfacet > facet normal 1 0 0 outer loop vertex 1 1 0 vertex 1 0 1 vertex > 1 0 1 endloop endfacet > facet normal 1 0 0 outer loop vertex 1 0 1 vertex 1 1 0 vertex > 1 1 0 endloop endfacet > endsolid OpenSCAD_Model > > Unlike what Wikipedia https://en.wikipedia.org/wiki/STL_%28file_format%29 > makes me expect, there are twice as many facets listed as a cube has faces, > and each facet points only to two vertices. I haven't investigated so far > whether this is due to an OpenSCAD bug or inappropriate Wikipedia > information. > > As to the question on the usefulness of projective geometry extensions to > OpenSCAD, I fail to see the usefulness of it. Yes, the display looks nicer, > and you can easily program tapers, but how often is that used? So my vote > is > against it, as is my vote against extensions to multmatrix(). Here I would > rather follow the philosophy projected with OpenSCAD2: simpler is better, > and deprecate multmatrix(), because it requires so much background in > mathematics to use it effectively. The useful portions of multmatrix() have > already been extracted into other transformations, as this program segment > shows: > > TranslatMatrix= [ [1, 0, 0, 10], > [0, 1, 0, 20], > [0, 0, 1, 30], > [0, 0, 0, 1] > ]; > ScaleMatrix= [ [1, 0, 0, 0], > [0, 1/2, 0, 0], > [0, 0, 1/3, 0], > [0, 0, 0, 1] > ]; > Rotate_Around_X=[ [1, 0, 0, 0], //source: > https://en.wikipedia.org/wiki/Rotation_formalisms_in_three_dimensions > [0, cos(30), -sin(30), 0], > [0, sin(30), cos(30), 0], > [0, 0, 0, 1] > ]; > Rotate_Around_Y=[ [cos(30), 0, sin(30), 0], > [ 0, 1, 0, 0], > [-sin(30), 0,cos(30), 0], > [0, 0, 0, 1] > ]; > Rotate_Around_Z=[ [cos(30), -sin(30), 0, 0], > [sin(30), cos(30), 0, 0], > [0, 0, 1, 0], > [0, 0, 0, 1] > ]; > //SkewMatrix= // source: > > https://en.wikipedia.org/wiki/Rotation_matrix#Skew_parameters_via_Cayley.27s_formula > // https://en.wikipedia.org/wiki/Cayley_transform > // https://en.wikipedia.org/wiki/Skew-symmetric_matrix > > //T_Simple(); > //T_mult(); > //S_Simple(); > //S_mult(); > //R_X_Simple(); > //R_X_mult(); > //R_Y_mult(); > R_Z_mult(); > > > module T_Simple() //this is one way of doing a translation > translate([10,20,30]) > cube([10,20,30]); > module T_mult() //this is another way of doing the same translation > multmatrix(m = TranslatMatrix) > cube([10,20,1/3]); > module S_Simple() //this is one way of doing scaling > scale([1,1/2,1/3]) > cube([10,20,30]); > module S_mult() //this is another way of doing the same scaling > multmatrix(m = ScaleMatrix) > cube([10,20,30]); > module R_X_Simple() //this is one way of doing a rotation around the x > axis > rotate(30,[1,0,0]) > cube([10,20,30]); > module R_X_mult() //this is another way of doing the same rotation > around > the x axis > multmatrix(m = Rotate_Around_X) > cube([10,20,30]); > module R_Y_mult() //this is a rotation around the y axis > multmatrix(m = Rotate_Around_Y) > cube([10,20,30]); > module R_Z_mult() //this is a rotation around the z axis > multmatrix(m = Rotate_Around_Z) > cube([10,20,30]); > > As far as I know, skew or shear transformations currently require the use > of > multmatrix(), but then who uses them? > Because Marius Kintel asked for them, I outline here another > transformation: > offset. > > $fn=50; > Diameter=2; // diameter of sphere from which ellipsoid is created > Offset=0.1*Diameter; > MaxDim=[3*Diameter,1*Diameter,.5*Diameter]; // long axes of ellipsoid > > MakeOffset(); > MakeCutout(); > TestPosition(); > > module MakeOffset() > scale([1-2*Offset/MaxDim[0],1-2*Offset/MaxDim[1],1-2*Offset/MaxDim[2]]) > // for a true offset, MaxDim[...] needs to be replaced with the norm of > each > vertex for the ellipsoid > Ellipsoid(); > module TestPosition() > translate([MaxDim[0]/2-Offset/2,0,0]) sphere(d=Offset); > translate([0,-(MaxDim[1]/2-Offset/2),0]) sphere(d=Offset); > translate([0,0,MaxDim[2]/2-Offset/2]) sphere(d=Offset); > module MakeCutout() > difference() > { Ellipsoid(); > translate([0,-15,15]) cube([70,30,30], center=true); > } > module Ellipsoid() > scale([MaxDim[0]/Diameter,MaxDim[1]/Diameter,MaxDim[2]/Diameter]) > sphere(d=Diameter); > > It doesn't quite work in userspace, but comes pretty close. One line, as > commented, needs access to the vertex vectors, which OpenSCAD does not > readily provide. Work for someone with knowledge of the internals. > <http://forum.openscad.org/file/n16588/Offset.jpg> > The yellow color in the cutout indicates a problem OpenSCAD has with the > faces created by module MakeCutout(). Probably inside-out faces. They were > made with version 2015.03-1. > > wolf > > > > > -- > View this message in context: > http://forum.openscad.org/Non-Linear-Transformations-tp14539p16588.html > Sent from the OpenSCAD mailing list archive at Nabble.com. > > _______________________________________________ > OpenSCAD mailing list > Discuss@lists.openscad.org > http://lists.openscad.org/mailman/listinfo/discuss_lists.openscad.org > > >
MK
Marius Kintel
Tue, Mar 22, 2016 5:17 AM

On Mar 19, 2016, at 11:46 AM, doug moen doug@moens.org wrote:

Does anybody on the list have a better understanding of this? What are all the things that would go wrong if we tried to extend multmatrix to support projective transformations?

From the top of my head, I don’t think much can go wrong. It’s still just a linear transformation.
Mapping to infinity is only possible through a division by zero when normalizing the resulting homogeneous coordinate, right?
..so that’s roughly similar to having inf values in an affine transformation matrix.

Practically, we’re limited to affine transformation since that’s all CGAL supports for Nef polyhedrons.

-Marius

> On Mar 19, 2016, at 11:46 AM, doug moen <doug@moens.org> wrote: > > Does anybody on the list have a better understanding of this? What are all the things that would go wrong if we tried to extend multmatrix to support projective transformations? > From the top of my head, I don’t think much can go wrong. It’s still just a linear transformation. Mapping to infinity is only possible through a division by zero when normalizing the resulting homogeneous coordinate, right? ..so that’s roughly similar to having inf values in an affine transformation matrix. Practically, we’re limited to affine transformation since that’s all CGAL supports for Nef polyhedrons. -Marius
P
Parkinbot
Tue, Mar 22, 2016 12:49 PM

A projection may be described by a multmatrix using a zero scale factor for
one dimension. So everything is fine. As Kintel says: CGAL is restricted to
affine transformations, so more general non-linear transformations can't be
offered as long as this restriction holds.

Well, linear_extrude() is not a transformation, rather a constructor. As
such it touches just the tip of the iceberg of what would be possible in
OpenSCAD, without even touching multmatrix. As Wolf wrote "Twist is
implemented as a succession of skew transformations." This is the door.

Earlier in this thread I've already opted for a nonlinear_extrude() or let's
say an "enhanced linear_extrude()" primitive that offers a richer
prototype
. A first step would be to also allow for negative height values -
linear_extrude is not 'linear' in this point. That maybe already on the todo
list. A second (eady) one would be to allow to specify a vector along which
extrusion occurs.

But of course much more is possible between linear_extrude() and sweep()
without leaving the land of affine operations. While sweep(), depending on
its implemetation, more or less expects an explicit description of each
frame, also more implicit path and operation descriptions would be possible.
E.g. extrusion could follow (well-defaulted) path vectors, scale vectors and
even orientation (rotation) vectors.

From the other side, also rotate_extrude() could be enriched to allow for a

height argument (definition of screws) or a given height path (scews with
nonlinear slopes).

Once function arguments are possible xxx_extrude anyway should be prepared
to work with them.

  • Rudolf -

--
View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p16656.html
Sent from the OpenSCAD mailing list archive at Nabble.com.

A projection may be described by a multmatrix using a zero scale factor for one dimension. So everything is fine. As Kintel says: CGAL is restricted to affine transformations, so more general non-linear transformations can't be offered as long as this restriction holds. Well, linear_extrude() is not a transformation, rather a constructor. As such it touches just the tip of the iceberg of what would be possible in OpenSCAD, without even touching multmatrix. As Wolf wrote "Twist is implemented as a succession of skew transformations." This is the door. Earlier in this thread I've already opted for a nonlinear_extrude() or let's say an "enhanced linear_extrude()" primitive that offers a *richer prototype*. A first step would be to also allow for negative height values - linear_extrude is not 'linear' in this point. That maybe already on the todo list. A second (eady) one would be to allow to specify a vector along which extrusion occurs. But of course much more is possible between linear_extrude() and sweep() without leaving the land of affine operations. While sweep(), depending on its implemetation, more or less expects an explicit description of each frame, also more implicit path and operation descriptions would be possible. E.g. extrusion could follow (well-defaulted) path vectors, scale vectors and even orientation (rotation) vectors. >From the other side, also rotate_extrude() could be enriched to allow for a height argument (definition of screws) or a given height path (scews with nonlinear slopes). Once function arguments are possible xxx_extrude anyway should be prepared to work with them. - Rudolf - -- View this message in context: http://forum.openscad.org/Non-Linear-Transformations-tp14539p16656.html Sent from the OpenSCAD mailing list archive at Nabble.com.