Initial Commit

This commit is contained in:
Mario Voigt (Leyghis) 2019-03-01 23:14:59 +01:00
commit 069fda9a45
5 changed files with 5561 additions and 0 deletions

1719
eggbot_hatch.py Normal file

File diff suppressed because it is too large Load Diff

143
plaster.inx Normal file
View File

@ -0,0 +1,143 @@
<?xml version="1.0" encoding="UTF-8"?>
<inkscape-extension xmlns="http://www.inkscape.org/namespace/inkscape/extension">
<_name>The Plaster Tool - #YourMachine001</_name>
<id>plaster_YourMachine001</id>
<dependency type="executable" location="extensions">plaster.py</dependency>
<dependency type="executable" location="extensions">inkex.py</dependency>
<param name="main_tabs" type="notebook">
<page name="tab_export" gui-text=" Export it! ">
<param name="desc_0" type="description" appearance="header">File export settings</param>
<param name="directory" type="string" _gui-text="Export directory:">~/Desktop</param>
<param name="filename" type="string" _gui-text="Export filename:">output.gcode</param>
<param name="add-numeric-suffix-to-filename" type="boolean" _gui-text="Add numeric suffix to filename (*.* to *_XXXX.*)">false</param>
<param name="show-output-path" type="boolean" _gui-text="Show popup containg output directory of saved file">false</param>
<param name="desc_1" type="description" appearance="header">InkScape performance</param>
<param name="draw-calculation-paths" type="boolean" _gui-text="Draw calculated paths">false</param>
<param name="desc_2" type="description">(disable for slow computers or huge images; raises performance)</param>
</page>
<page name="tab_speed_settings" gui-text=" Speed/geometry settings ">
<param name="travel-speed" type="int" min="1" max="99999" _gui-text="Travel speed (mm/min or in/mm):">7000</param>
<param name="tooling-speed" type="int" min="1" max="99999" _gui-text="Tooling speed (mm/min or in/mm):">2000</param>
<param name="delay-time" type="int" min="0" max="5000" _gui-text="Servo speed/dwell time/delay (ms)">200</param>
<param name="biarc-max-split-depth" type="int" min="1" max="100" _gui-text="BiArc maximum split depth:">4</param>
<param name="biarc-tolerance" type="float" precision="4" _gui-text="BiArc tolerance:">1</param>
<param name="scale-uniform" type="float" precision="4" min="-99999" max="99999" _gui-text="Uniform XY scale (%):">100,0</param>
<param name="coordinates-unit" type="enum" _gui-text="Units:">
<item value="MM">mm</item>
<item value="IN">in</item>
</param>
</page>
<page name="tab_tool_settings" gui-text=" Tool settings ">
<param name="desc_3" type="description" appearance="header">Pen adjusting</param>
<param name="pen-index" type="int" min="0" max="10" _gui-text="Servo (pen tool) index P">0</param>
<param name="pen-up-angle" type="float" precision="4" min="0.0" max="180.0" _gui-text="Pen up angle S(0,0 .. 180,0°):">33,0</param>
<param name="pen-down-angle" type="float" precision="4" min="0.0" max="180.0" _gui-text="Pen down angle S(0,0 .. 180,0°):">45,0</param>
<param name="desc_4" type="description" appearance="header">Laser adjusting</param>
<param name="tool-index" type="int" min="0" max="10" _gui-text="Laser tool index T">0</param>
<param name="laserpower" type="float" precision="4" min="0" max="100" _gui-text="Laser power S(0 .. 100 %):">0</param>
</page>
<page name="tab_loops" gui-text=" Loops/Incrementer ">
<param name="repeatings" type="int" min="0" max="9999" _gui-text="Loops ('0' means single run):">0</param>
<param name="repeatings-command" type="string" _gui-text="Command(s) before repeating:">G4 P1000; wait 1 second</param>
<param name="repeatings-offset-x" type="float" precision="4" min="-99999" max="99999" _gui-text="X-Offset (in or mm):">0.000</param>
<param name="repeatings-offset-y" type="float" precision="4" min="-99999" max="99999" _gui-text="Y-Offset (in or mm):">0.000</param>
<param name="scale-increment" type="float" precision="4" min="-99999" max="99999" _gui-text="Scale increment (+/- %):">0,0</param>
<param name="repeatings-mode" type="enum" _gui-text="Mode:">
<item value="partial">[Partial] Repeat geometry outline only</item>
<item value="full">[Full] Repeat whole program</item>
</param>
<param name="repeatings-pen-increment" type="float" precision="4" min="-180.0" max="180.0" _gui-text="Pen up/down angle increment (+/- °):">0,0</param>
<param name="laserpower-increment" type="float" precision="4" min="0.0" max="100.0" _gui-text="Laser power increment (+/- % of max. power):">0,0</param>
</page>
<page name="tab_randomize" gui-text=" Randomize ">
<param name="desc_5" type="description" appearance="header">Random laser power</param>
<param name="randomize-laserpower" type="boolean" _gui-text="Randomize laser power for each line segment">false</param>
<param name="randomize-laserpower-lowerval" type="float" precision="4" min="0" max="100" _gui-text="Random laser power, lower bound (rel %):">0,0</param>
<param name="randomize-laserpower-upperval" type="float" precision="4" min="0" max="100" _gui-text="Random laser power, upper bound (rel %):">0,0</param>
<param name="desc_6" type="description" appearance="header">Random down position pen angle (pressure)</param>
<param name="randomize-penangle" type="boolean" _gui-text="Randomize pen angle for each line segment">false</param>
<param name="randomize-penangle-lowerval" type="float" precision="4" min="0.00001" max="180.0" _gui-text="Random pen angle, lower bound (rel °):">0,0</param>
<param name="randomize-penangle-upperval" type="float" precision="4" min="0.00001" max="180.0" _gui-text="Random pen angle, upper bound (rel °):">0,0</param>
<param name="desc_7" type="description" appearance="header">Random tooling speed</param>
<param name="randomize-speed" type="boolean" _gui-text="Randomize tooling speed for each line segment">false</param>
<param name="randomize-speed-lowerval" type="float" precision="4" min="0.00001" max="99999" _gui-text="Random tooling speed, lower bound (rel mm/min or in/mm):">0,0</param>
<param name="randomize-speed-upperval" type="float" precision="4" min="0.00001" max="99999" _gui-text="Random tooling speed, upper bound (rel mm/min or in/mm):">0,0</param>
<param name="desc_8" type="description">Note: minimum tooling speed is 1.0</param>
<param name="desc_9" type="description" appearance="header">Random dwell time</param>
<param name="randomize-delay" type="boolean" _gui-text="Randomize dwell time">false</param>
<param name="randomize-delay-lowerval" type="float" precision="4" min="0.00001" max="99999" _gui-text="Random dwell time, lower bound (rel ms):">0,0</param>
<param name="randomize-delay-upperval" type="float" precision="4" min="0.00001" max="99999" _gui-text="Random dwell time, upper bound (rel ms):">0,0</param>
</page>
<page name="tab_firmware" gui-text=" Firmware/GCode ">
<param name="desc_9" type="description" appearance="header">Machine type</param>
<param name="machine-type" type="enum" _gui-text="Generate code for:">
<item value="laser">Laser</item>
<item value="plotter">Plotter</item>
</param>
<param name="desc_10" type="description" appearance="header">Controller firmware/wiring</param>
<param name="gcode-flavour-preset" type="optiongroup" _gui-text="Select preset:">
<option value="repetier_laser">Repetier (with laser diode on tool pin, takes M452 + M3/M5 commands)</option>
<option value="repetier_fan">Repetier (with laser diode on fan pin, takes M106 command)</option>
<!--<option value="marlin">Marlin (n.a. yet)</option>
<option value="mk4duo">MK4duo (n.a. yet)</option>
<option value="reprap">RepRap (n.a. yet)</option>
<option value="grbl">GRBL (n.a. yet)</option>
<option value="smoothie">Smoothie (n.a. yet)</option>-->
</param>
<param name="desc_11" type="description" appearance="header">Other GCode modifications</param>
<param name="header-command" type="string" _gui-text="Header command(s):">;plugin code by Mario (Stoutwind)</param>
<param name="footer-command" type="string" _gui-text="Footer command(s):">;plugin code by Mario (Stoutwind)</param>
<param name="desc_12" type="description" appearance="header">Safety</param>
<param name="auto-homing" type="boolean" _gui-text="X/Y Homing at the beginning">true</param>
<param name="auto-disable-tool" type="boolean" _gui-text="Disable tool at the end (turn off laser diode/unpower servo motor)">true</param>
</page>
<page name="tab_help" gui-text=" About ">
<param name="desc_h_0" type="description" appearance="header">This dirty program creates GCode in x,y dimensions for cartesian CNC machines with tool type plotter/laser. It can handle a single servo motor for pen up and down movements. The z dimension is not implemented. Also multiple tools are not supported. Please define the hardware index of your single laser diode (tool index) and/or pen servo motor (servo index) to use this plugin. It's just intended to use with simple machine constructions. If you build a multi tool machine like a 3D printer with integrated/changeable sub tools for milling, 3D scanning, plotting or laser cutting, you just should pimp this plugin for your own needs.</param>
</page>
<page name="tab_faq" gui-text=" FAQ ">
<param name="desc_f_1" type="description">1) Header, Footer, Repeat commands: Separate each line with '\n' to put more commands on input line</param>
<param name="desc_f_2" type="description">2) Usage of servo motor (common syntax): M340 P°TOOLINDEX° S°ANGLE°</param>
<param name="desc_f_3" type="description">3) Export directory: Put in '~/Desktop' to quickly push the file to your Desktop</param>
<param name="desc_f_4" type="description">4) Pen Up/Down Increment (+/-): You can use this to regulate the pressure or to grind deeper with your pen/cutter/... for each loop</param>
<param name="desc_f_5" type="description">5) X/Y-Offset: Use this for quickly creating a pattern in X, Y or combined XY directions</param>
<param name="desc_f_6" type="description">6) Tooling speed: Define the speed of your pen or laser diode in mm/min or in/min</param>
<param name="desc_f_7" type="description">7) If your image does not update scale and returns wrong dimensions in GCode, please delete orientation points group 'gcodetools' and run this plugin again!</param>
<param name="desc_f_8" type="description">8) Pen moves in wrong direction: Just swap Pos 1 and Pos 2!</param>
<param name="desc_f_9" type="description">9) Use of this plugin with multiple machines: If you hate to reconfigure this plugin each time you swap the machine just make use of a dirty trick: Just copy and rename the plaster.inx file into °ROOT°/share/extensions. You'll have to change the value "_name" and "id" below.</param>
</page>
<page name="tab_info" gui-text=" License/Version ">
<param name="desc_i_1" type="description" appearance="header">The Plaster (Plotter-Laser) Tool is based on ...</param>
<param name="desc_i_2" type="description">* Repetier Laser Tool (GNU GPL) from Hot-World GmbH & Co. KG (http://www.repetier.com)</param>
<param name="desc_i_3" type="description">* EggBot Hatch (GNU GPL v2) from Evil Mad Scientist (http://www.evilmadscientist.com)</param>
<param name="desc_i_4" type="description">* Inkscape Laser Tool Plug-in (GNU GPL) from JTECH Photonics (http://www.jtechphotonics.com)</param>
<param name="desc_i_4" type="description">* THLaser Laser Plug-in (GNU GPL) from think|haus (http://www.thinkhaus.org)</param>
<param name="desc_i_5" type="description">------------------------------------------------------------------------</param>
<param name="desc_i_6" type="description">(Re-)written by Mario Voigt from Stoutwind (https://stoutwind.de)</param>
<param name="desc_i_7" type="description">------------------------------------------------------------------------</param>
<param name="desc_i_8" type="description">Last update: 30.10.2016</param>
<param name="desc_i_9" type="description" appearance="header">you found a bug or got some fresh code? Just report to info@stoutwind.de. Thanks!</param>
</page>
</param>
<effect>
<effects-menu>
<submenu _name="Stoutwind Plaster Tool"/>
</effects-menu>
<object-type>path</object-type>
</effect>
<script>
<command reldir="extensions" interpreter="python">plaster.py</command>
</script>
</inkscape-extension>

3396
plaster.py Normal file

File diff suppressed because it is too large Load Diff

77
plaster_hatch.inx Normal file
View File

@ -0,0 +1,77 @@
<?xml version="1.0" encoding="UTF-8"?>
<inkscape-extension xmlns="http://www.inkscape.org/namespace/inkscape/extension">
<_name>Hatch fill</_name>
<id>plaster_hatch</id>
<dependency type="extension">org.inkscape.output.svg.inkscape</dependency>
<dependency type="executable" location="extensions">eggbot_hatch.py</dependency>
<dependency type="executable" location="extensions">inkex.py</dependency>
<dependency type="executable" location="extensions">simplepath.py</dependency>
<dependency type="executable" location="extensions">simpletransform.py</dependency>
<dependency type="executable" location="extensions">simplestyle.py</dependency>
<dependency type="executable" location="extensions">cubicsuperpath.py</dependency>
<dependency type="executable" location="extensions">cspsubdiv.py</dependency>
<dependency type="executable" location="extensions">bezmisc.py</dependency>
<dependency type="executable" location="extensions">plot_utils.py</dependency>
<param name="tab" type="notebook">
<page name="splash" _gui-text="Hatch Fill">
<_param name="Header" type="description" xml:space="preserve">
This extension fills each closed figure in your drawing
with a path consisting of back and forth drawn "hatch" lines.
If any objects are selected, then only those selected objects
will be filled.
Hatched figures will be grouped with their fills.
</_param>
<param name="hatchSpacing" type="float" min="0" max="1000" _gui-text=" Hatch spacing (px)">5.0</param>
<param name="hatchAngle" type="float" min="-360" max="360" _gui-text=" Hatch angle (degrees)">45</param>
<param name="crossHatch" type="boolean" _gui-text=" Crosshatch?">false</param>
<param name="reducePenLifts" type="boolean" _gui-text=" Connect nearby ends?">true</param>
<param name="hatchScope" type="float" min="1.1" max="5.0" _gui-text=" Range of end connections (default: 3)">3.0</param>
<param name="holdBackHatchFromEdges" type="boolean" _gui-text=" Inset fill from edges?">true</param>
<param name="holdBackSteps" type="float" min="0.1" max="10.0" _gui-text=" Inset distance (px) (default: 1)">1.0</param>
<param name="tolerance" type="float" min="0.1" max="100" _gui-text=" Tolerance (default: 20)">20.0</param>
</page>
<page name="info" _gui-text="More info...">
<_param name="aboutpage" type="description" xml:space="preserve">
Hatch spacing is the distance between hatch lines,
measured in units of screen pixels (px). Angles are in
degrees from horizontal; for example 90 is vertical.
The Crosshatch option will apply a second set of
hatches, perpendicular to the first.
The "Connect nearby ends" option will attempt to connect
nearby line ends with a smoothly flowing curve, to improve
the smoothness of plotting.
The Range parameter sets the distance (in hatch widths)
over which that option searches for segments to join.
Large values may result in hatches where you don't want
them. Consider using a value in the range of 2-4.
The Inset option allows you to hold back the edges of the
fill somewhat from the edge of your original object.
This can improve performance, as it allows you to more
reliably "color inside the lines" when using pens.
The hatches will be the same color and width
as the original object.
The Tolerance parameter affects how precisely
the hatches try to fill the input paths.</_param>
</page>
</param>
<effect needs-live-preview="true">
<object-type>all</object-type>
<effects-menu>
<submenu _name="Stoutwind Plaster Tool"/>
</effects-menu>
</effect>
<script>
<command reldir="extensions" interpreter="python">eggbot_hatch.py</command>
</script>
</inkscape-extension>

226
plot_utils.py Normal file
View File

@ -0,0 +1,226 @@
# plot_utils.py
# Common geometric plotting utilities for EiBotBoard
# https://github.com/evil-mad/plotink
#
# Intended to provide some common interfaces that can be used by
# EggBot, WaterColorBot, AxiDraw, and similar machines.
#
# Version 0.4, Dated February 22, 2016.
#
#
# The MIT License (MIT)
#
# Copyright (c) 2016 Evil Mad Scientist Laboratories
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.
from math import sqrt
import cspsubdiv
from bezmisc import *
def version():
return "0.3" # Version number for this document
def distance( x, y ):
'''
Pythagorean theorem!
'''
return sqrt( x * x + y * y )
def parseLengthWithUnits( str ):
'''
Parse an SVG value which may or may not have units attached
This version is greatly simplified in that it only allows: no units,
units of px, and units of %. Everything else, it returns None for.
There is a more general routine to consider in scour.py if more
generality is ever needed.
'''
u = 'px'
s = str.strip()
if s[-2:] == 'px':
s = s[:-2]
elif s[-2:] == 'in':
s = s[:-2]
u = 'in'
elif s[-2:] == 'mm':
s = s[:-2]
u = 'mm'
elif s[-2:] == 'cm':
s = s[:-2]
u = 'cm'
elif s[-1:] == '%':
u = '%'
s = s[:-1]
try:
v = float( s )
except:
return None, None
return v, u
def getLength( altself, name, default ):
'''
Get the <svg> attribute with name "name" and default value "default"
Parse the attribute into a value and associated units. Then, accept
no units (''), units of pixels ('px'), and units of percentage ('%').
'''
str = altself.document.getroot().get( name )
if str:
v, u = parseLengthWithUnits( str )
if not v:
# Couldn't parse the value
return None
elif ( u == '' ) or ( u == 'px' ):
return v
elif u == 'in' :
return (float( v ) * 90.0) #90 px per inch, as of Inkscape 0.91
elif u == 'mm':
return (float( v ) * 90.0 / 25.4)
elif u == 'cm':
return (float( v ) * 90.0 / 2.54)
elif u == '%':
return float( default ) * v / 100.0
else:
# Unsupported units
return None
else:
# No width specified; assume the default value
return float( default )
def getLengthInches( altself, name ):
'''
Get the <svg> attribute with name "name" and default value "default"
Parse the attribute into a value and associated units. Then, accept
units of inches ('in'), millimeters ('mm'), or centimeters ('cm')
'''
str = altself.document.getroot().get( name )
if str:
v, u = parseLengthWithUnits( str )
if not v:
# Couldn't parse the value
return None
elif u == 'in' :
return v
elif u == 'mm':
return (float( v ) / 25.4)
elif u == 'cm':
return (float( v ) / 2.54)
else:
# Unsupported units
return None
def subdivideCubicPath( sp, flat, i=1 ):
"""
Break up a bezier curve into smaller curves, each of which
is approximately a straight line within a given tolerance
(the "smoothness" defined by [flat]).
This is a modified version of cspsubdiv.cspsubdiv(). I rewrote the recursive
call because it caused recursion-depth errors on complicated line segments.
"""
while True:
while True:
if i >= len( sp ):
return
p0 = sp[i - 1][1]
p1 = sp[i - 1][2]
p2 = sp[i][0]
p3 = sp[i][1]
b = ( p0, p1, p2, p3 )
if cspsubdiv.maxdist( b ) > flat:
break
i += 1
one, two = beziersplitatt( b, 0.5 )
sp[i - 1][2] = one[1]
sp[i][0] = two[2]
p = [one[2], one[3], two[1]]
sp[i:1] = [p]
def checkLimits( value, lowerBound, upperBound ):
#Check machine size limit; truncate at edges
if (value > upperBound):
return upperBound, True
if (value < lowerBound):
return lowerBound, True
return value, False
def vFinal_Vi_A_Dx(Vinitial,Acceleration,DeltaX):
'''
Kinematic calculation: Final velocity with constant linear acceleration.
Calculate and return the (real) final velocity, given an initial velocity,
acceleration rate, and distance interval.
Uses the kinematic equation Vf^2 = 2 a D_x + Vi^2, where
Vf is the final velocity,
a is the acceleration rate,
D_x (delta x) is the distance interval, and
Vi is the initial velocity.
We are looking at the positive root only-- if the argument of the sqrt
is less than zero, return -1, to indicate a failure.
'''
FinalVSquared = ( 2 * Acceleration * DeltaX ) + ( Vinitial * Vinitial )
if (FinalVSquared > 0):
return sqrt(FinalVSquared)
else:
return -1
def vInitial_VF_A_Dx(VFinal,Acceleration,DeltaX):
'''
Kinematic calculation: Maximum allowed initial velocity to arrive at distance X
with specified final velocity, and given maximum linear acceleration.
Calculate and return the (real) initial velocity, given an final velocity,
acceleration rate, and distance interval.
Uses the kinematic equation Vi^2 = Vf^2 - 2 a D_x , where
Vf is the final velocity,
a is the acceleration rate,
D_x (delta x) is the distance interval, and
Vi is the initial velocity.
We are looking at the positive root only-- if the argument of the sqrt
is less than zero, return -1, to indicate a failure.
'''
IntialVSquared = ( VFinal * VFinal ) - ( 2 * Acceleration * DeltaX )
if (IntialVSquared > 0):
return sqrt(IntialVSquared)
else:
return -1
def dotProductXY( inputVectorFirst, inputVectorSecond):
temp = inputVectorFirst[0] * inputVectorSecond[0] + inputVectorFirst[1] * inputVectorSecond[1]
if (temp > 1):
return 1
elif (temp < -1):
return -1
else:
return temp