# Fun with math and CNC  (Linuxcnc)



## skunkworks (Oct 7, 2020)

Still playing with spindle synced motion - 






Most expensive bolt?


----------



## alloy (Oct 8, 2020)

I'd love to see the code you wrote for that and an explination of the math you used.   

You have intrigued me.  Go my little pea brain working this morning 

I wonder if my lathe with a Fanuc OT would do that?


----------



## skunkworks (Oct 8, 2020)

Heh - It is a bit of trig..  Mostly.  I started out trying to figure out how to create a N shaped polygon then decided to look on the internet and found a nice little formula.









						Is there an equation to describe regular polygons?
					

For example, the square can be described with the equation $|x| + |y| = 1$. So is there a general equation that can describe a regular polygon (in the 2D Cartesian plane?), given the number of sides




					math.stackexchange.com
				




Linuxcnc, because the realtime layer is in the computer, give you quite a bit of control over motion..  

So basically - I am reading the spindle encoder position and then calculating were the axis should be (this is a realtime component within the hardware abstraction layer of linuxcnc. (this is done at the realtime servo thread which on the lathe is IIRC 3khz.

I don't have the latest code - and I am a messy coder...  


```
//   This is a component for Linuxcnc HAL
//   Copyright 2020 Sam Sokolik <samcoinc@gmail.com>
//
//   This program is free software; you can redistribute it and/or modify
//   it under the terms of the GNU General Public License as published by
//   the Free Software Foundation; either version 2 of the License, or
//   (at your option) any later version.
//
//   This program is distributed in the hope that it will be useful,
//   but WITHOUT ANY WARRANTY; without even the implied warranty of
//   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//   GNU General Public License for more details.
//
//   You should have received a copy of the GNU General Public License
//   along with this program; if not, write to the Free Software
//   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
component polygon "Create a spindle synced motion that carves a polygon using eoffset inputs.  Assumes positive rotation.";

pin in bit enable;
pin in bit enablexslave "enables connecting x postion to radius";
pin in float xpos "connect to the x axis potion in hal";
pin out float xposaten "when componant is enabled - grab current x postion";
pin in unsigned numsides=3 "Number of sides in the polygon";
pin in float inscribedradius=1 "inscribed radius of the polygon";
pin in float cutterdiam "cutter diameter";
pin in float eoffsetscale "scale that eoffset is set to.";
pin in float toolang "angle difference between index and actual tool poition";
pin in float polyang "angle of the polygon";
pin in float spindlepos "Spindle position scaled to 1 per rev";
pin out float spindlerad "Spindle postion in radians";
pin out float polyradius "radious of the polygon at given spindle position";
pin out float xoffset "x offset to send to offset componant";
pin out float yoffset "y offset to send to the offset componant";
pin out signed xeoffset "x eoffset output";
pin out signed yeoffset "y eoffset output";
pin out bit isindex "set index enable only once";
pin io bit indexenable "hooked to index enable of encoder";

function _;
license "GPL";
;;
#include <rtapi_math.h>
#define PI 3.14159265358979323846
float spinang;
float scale;
float spinangoffset;
float polyangoffset;
float radiusslave=0;

    if (!enable) {
        xoffset=0;
        yoffset=0;
        xeoffset=0;
        yeoffset=0;
        isindex = false;
        xposaten = 0;
        return;
    }

// only set index enable once
    if (enable && !isindex) {
    isindex = true;
    indexenable = true;
        if (enablexslave){
            xposaten=xpos;
            }
        return;
    }

// wait for spindle index before actually enabling
    if (enable && isindex && indexenable){
        return;
    }

//convert spinangoffset to ratio.. for adding to spindle pos - plus a couple rotations
//so the spindle position isn't negative
spinangoffset = (toolang/360-polyang/360)+2;
polyangoffset = (polyang/360)*2*PI;

//formual I found is for circumscribed - convert to inscribed - makes more sense.


spinang = ((spindlepos + spinangoffset) - (int)(spindlepos + spinangoffset))*2*PI;

//calculate radius based on if x moves
    if (enablexslave){
        radiusslave=xpos-xposaten;
    }
scale=(inscribedradius-radiusslave)/cos(PI/numsides);
polyradius = ((cos(PI/numsides)/cos((fmod(spinang, (2*PI/numsides))-PI/numsides)))*scale-cutterdiam/2);




//actual offsets applied - could be used for offset componant.
xoffset = cos(spinang+polyangoffset)*polyradius * -1-(radiusslave);
yoffset = sin(spinang+polyangoffset)*polyradius;

//counts for use with eoffset functionality
xeoffset = xoffset / eoffsetscale;
yeoffset = yoffset / eoffsetscale;

spindlerad = spinang;
```


----------



## alloy (Oct 8, 2020)

Doesn't look like I can do it, but was fun trying to wrap my head around it


----------

