This repository has been archived on 2023-03-25. You can view files and clone it, but cannot push or open issues or pull requests.
mightyscape-0.92-deprecated/extensions/fablabchemnitz_raster2laser.py

632 lines
24 KiB
Python
Raw Normal View History

2019-11-14 20:05:10 +01:00
'''
# ----------------------------------------------------------------------------
# Copyright (C) 2014 305engineering <305engineering@gmail.com>
# Original concept by 305engineering.
#
# "THE MODIFIED BEER-WARE LICENSE" (Revision: my own :P):
# <305engineering@gmail.com> wrote this file. As long as you retain this notice you
# can do whatever you want with this stuff (except sell). If we meet some day,
# and you think this stuff is worth it, you can buy me a beer in return.
#
# 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.
# ----------------------------------------------------------------------------
'''
import sys
import os
import re
sys.path.append('/usr/share/inkscape/extensions')
sys.path.append('/Applications/Inkscape.app/Contents/Resources/extensions')
import subprocess
import math
import inkex
import fablabchemnitz_png
import array
class GcodeExport(inkex.Effect):
######## Invoked by _main()
def __init__(self):
"""init the effect library and get options from gui"""
inkex.Effect.__init__(self)
# Image export options
self.OptionParser.add_option("-d", "--directory",action="store", type="string", dest="directory", default="/home/",help="Directory for files") ####check_dir
self.OptionParser.add_option("-f", "--filename", action="store", type="string", dest="filename", default="-1.0", help="File name")
self.OptionParser.add_option("","--add-numeric-suffix-to-filename", action="store", type="inkbool", dest="add_numeric_suffix_to_filename", default=True,help="Add numeric suffix to filename")
self.OptionParser.add_option("","--bg_color",action="store",type="string",dest="bg_color",default="",help="")
self.OptionParser.add_option("","--resolution",action="store", type="int", dest="resolution", default="5",help="") #Usare il valore su float(xy)/resolution e un case per i DPI dell export
# How to convert to grayscale
self.OptionParser.add_option("","--grayscale_type",action="store", type="int", dest="grayscale_type", default="1",help="")
# Conversion Mode in Black and White
self.OptionParser.add_option("","--conversion_type",action="store", type="int", dest="conversion_type", default="1",help="")
# Modal Options
self.OptionParser.add_option("","--BW_Max",action="store", type="int", dest="BW_Max", default="255",help="")
self.OptionParser.add_option("","--Laser_Min",action="store", type="int", dest="Laser_Min", default="40",help="")
self.OptionParser.add_option("","--Dim_Test_Times",action="store", type="int", dest="Dim_Test_Times", default="3",help="")
self.OptionParser.add_option("","--BW_threshold",action="store", type="int", dest="BW_threshold", default="128",help="")
self.OptionParser.add_option("","--grayscale_resolution",action="store", type="int", dest="grayscale_resolution", default="1",help="")
#Black Velocity and Moving
self.OptionParser.add_option("","--speed_ON",action="store", type="int", dest="speed_ON", default="1200",help="")
# Mirror Y
self.OptionParser.add_option("","--flip_y",action="store", type="inkbool", dest="flip_y", default=False,help="")
# Homing
self.OptionParser.add_option("","--homing",action="store", type="int", dest="homing", default="4",help="")
# Commands
self.OptionParser.add_option("","--laseron", action="store", type="string", dest="laseron", default="M106", help="")
self.OptionParser.add_option("","--laseroff", action="store", type="string", dest="laseroff", default="M107", help="")
# Preview = BN image only
self.OptionParser.add_option("","--preview_only",action="store", type="inkbool", dest="preview_only", default=False,help="")
#inkex.errormsg("BLA BLA BLA Message to display") #DEBUG
######## Invoked by __init __ ()
######## Here everything is done
def effect(self):
current_file = self.args[-1]
bg_color = self.options.bg_color
##Implementare check_dir
if (os.path.isdir(self.options.directory)) == True:
##CODE THAT IS THE DIRECTORY
#inkex.errormsg("OK") #DEBUG
#I add a suffix to the filename to not overwrite the files
if self.options.add_numeric_suffix_to_filename :
dir_list = os.listdir(self.options.directory) #List all the files in the work directory
temp_name = self.options.filename
max_n = 0
for s in dir_list :
r = re.match(r"^%s_0*(\d+)%s$"%(re.escape(temp_name),'.png' ), s)
if r :
max_n = max(max_n,int(r.group(1)))
self.options.filename = temp_name + "_" + ( "0"*(4-len(str(max_n+1))) + str(max_n+1) )
#Generate file paths to use
suffix = ""
if self.options.conversion_type == 1:
suffix = "_BWfix_"+str(self.options.BW_threshold)+"_"
elif self.options.conversion_type == 2:
suffix = "_BWrnd_"
elif self.options.conversion_type == 3:
suffix = "_H_"
elif self.options.conversion_type == 4:
suffix = "_Hrow_"
elif self.options.conversion_type == 5:
suffix = "_Hcol_"
else:
if self.options.grayscale_resolution == 1:
suffix = "_Gray_256_"
elif self.options.grayscale_resolution == 2:
suffix = "_Gray_128_"
elif self.options.grayscale_resolution == 4:
suffix = "_Gray_64_"
elif self.options.grayscale_resolution == 8:
suffix = "_Gray_32_"
elif self.options.grayscale_resolution == 16:
suffix = "_Gray_16_"
elif self.options.grayscale_resolution == 32:
suffix = "_Gray_8_"
else:
suffix = "_Gray_"
pos_file_png_exported = os.path.join(self.options.directory,self.options.filename+".png")
pos_file_png_BW = os.path.join(self.options.directory,self.options.filename+suffix+"preview.png")
pos_file_gcode = os.path.join(self.options.directory,self.options.filename+suffix+".gcode")
posDimTest_file_gcode = os.path.join(self.options.directory,self.options.filename+suffix+"DimTest.gcode")
#Export the image to PNG
self.exportPage(pos_file_png_exported,current_file,bg_color)
#TO DO
#Manipulate the PNG image to generate the Gcode file
self.PNGtoGcode(pos_file_png_exported,pos_file_png_BW,pos_file_gcode)
if self.options.Dim_Test_Times >= 1:
self.exportDimensionTest(pos_file_png_exported, pos_file_png_BW, posDimTest_file_gcode)
else:
inkex.errormsg("Directory does not exist! Please specify existing directory!")
######## EXPORT IMAGE IN PNG
######## Invoked by effect ()
def exportPage(self,pos_file_png_exported,current_file,bg_color):
######## CREATING THE FILE PNG ########
#Create the image inside the folder named "pos_file_png_exported"
#-d 127 = resolution 127DPI => 5 pixels / mm 1pixel = 0.2mm
###command="inkscape -C -e \"%s\" -b\"%s\" %s -d 127" % (pos_file_png_exported,bg_color,current_file)
if self.options.resolution == 1:
DPI = 25.4
elif self.options.resolution == 2:
DPI = 50.8
elif self.options.resolution == 5:
DPI = 127
else:
DPI = 254
command="inkscape -C -e \"%s\" -b\"%s\" %s -d %s" % (pos_file_png_exported,bg_color,current_file,DPI) #Command from command line to export to PNG
p = subprocess.Popen(command, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
return_code = p.wait()
f = p.stdout
err = p.stderr
######## Create a dimensional test of image
def exportDimensionTest(self,pos_file_png_exported,pos_file_png_BW,posDimTest_file_gcode):
#if self.options.Dim_Test_Times > 0:
reader = fablabchemnitz_png.Reader(pos_file_png_exported)#PNG files generated
w, h, pixels, metadata = reader.read_flat()
file_testgcode = open(posDimTest_file_gcode, 'w') #Create the dimenstional test file
file_testgcode.write('; Generated with:\n; "Raster 2 Laser Gcode generator"\n; by 305 Engineering\n; With a remix by VE7FRG\n;\n;\n')
file_testgcode.write('G21; Set units to millimeters\n')
file_testgcode.write('G90; Use absolute coordinates\n')
file_testgcode.write('G92; Coordinate Offset\n')
if self.options.homing == 1:
file_testgcode.write('G28 X0 Y0; home all axes\n')
file_testgcode.write('M42 P44 S0; Turn on LEDs\n')
file_testgcode.write('M42 P64 S0; Turn on VENT Fans\n')
elif self.options.homing == 2:
file_testgcode.write('$H; home all axes\n')
elif self.options.homing == 4:
file_testgcode.write('G28; home all axes\n')
file_testgcode.write('G92 X-47 Y-27; Coordinate Offset for CR-10 Mini\n')
file_testgcode.write('G0 Z100; Set laser head 100mm above surface\n')
else:
pass
file_testgcode.write(self.options.laseron + ' S' + str(self.options.Laser_Min) + '\n')
file_testgcode.write('; This is the number of width: '+ str(w) + '\n')
file_testgcode.write('; This is the number of height: '+ str(h) + '\n')
file_testgcode.write('; This is the number of tests: '+ str(self.options.Dim_Test_Times) + '\n')
file_testgcode.write('; This is the resolution number '+ str(self.options.resolution) + '\n')
p=1
while p <= self.options.Dim_Test_Times:
file_testgcode.write('G1 X' + str(w / self.options.resolution) + '\n')
file_testgcode.write('G1 Y' + str(h / self.options.resolution) + '\n')
file_testgcode.write('G1 X0\n')
file_testgcode.write('G1 Y0\n')
p = p+1
file_testgcode.write(self.options.laseroff + '\n')
file_testgcode.write('M42 P44 S255; Turn on LEDs\n')
file_testgcode.close()
######## CREATE IMAGE IN B / W AND THEN GENERATE GCODE
######## Richiamata da effect()
def PNGtoGcode(self,pos_file_png_exported,pos_file_png_BW,pos_file_gcode):
######## CREATE IMAGE IN GRAY SCALE ########
#I scroll the image and make it a list array
reader = fablabchemnitz_png.Reader(pos_file_png_exported)#PNG files generated
w, h, pixels, metadata = reader.read_flat()
matrice = [[255 for i in range(w)]for j in range(h)] #List al posto di un array
#I write a new image in 8bit Gray scale
#Pixel by pixel copy
if self.options.grayscale_type == 1:
#0.21R + 0.71G + 0.07B
for y in range(h): # Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
matrice[y][x] = int(pixels[pixel_position]*0.21 + pixels[(pixel_position+1)]*0.71 + pixels[(pixel_position+2)]*0.07)
elif self.options.grayscale_type == 2:
#(R+G+B)/3
for y in range(h): #Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
matrice[y][x] = int((pixels[pixel_position] + pixels[(pixel_position+1)]+ pixels[(pixel_position+2)]) / 3 )
elif self.options.grayscale_type == 3:
#R
for y in range(h): # Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
matrice[y][x] = int(pixels[pixel_position])
elif self.options.grayscale_type == 4:
#G
for y in range(h): # Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
matrice[y][x] = int(pixels[(pixel_position+1)])
elif self.options.grayscale_type == 5:
#B
for y in range(h): # Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
matrice[y][x] = int(pixels[(pixel_position+2)])
elif self.options.grayscale_type == 6:
#Max Color
for y in range(h): # Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
list_RGB = pixels[pixel_position] , pixels[(pixel_position+1)] , pixels[(pixel_position+2)]
matrice[y][x] = int(max(list_RGB))
else:
#Min Color
for y in range(h): # Y ranges from 0 to h-1
for x in range(w): # X varies from 0 to w-1
pixel_position = (x + y * w)*4 if metadata['alpha'] else (x + y * w)*3
list_RGB = pixels[pixel_position] , pixels[(pixel_position+1)] , pixels[(pixel_position+2)]
matrice[y][x] = int(min(list_RGB))
####Master matrix contains the grayscale image
######## GENERATE BLACK AND BLACK IMAGE ########
#Scorro matrice and generate matrice_BN
B=255
N=0
matrice_BN = [[255 for i in range(w)]for j in range(h)]
if self.options.conversion_type == 1:
#B/W fixed threshold
soglia = self.options.BW_threshold
for y in range(h):
for x in range(w):
if matrice[y][x] >= soglia :
matrice_BN[y][x] = B
else:
matrice_BN[y][x] = N
elif self.options.conversion_type == 2:
#B/W random threshold
from random import randint
for y in range(h):
for x in range(w):
soglia = randint(20,235)
if matrice[y][x] >= soglia :
matrice_BN[y][x] = B
else:
matrice_BN[y][x] = N
elif self.options.conversion_type == 3:
#Halftone
Step1 = [[B,B,B,B,B],[B,B,B,B,B],[B,B,N,B,B],[B,B,B,B,B],[B,B,B,B,B]]
Step2 = [[B,B,B,B,B],[B,B,N,B,B],[B,N,N,N,B],[B,B,N,B,B],[B,B,B,B,B]]
Step3 = [[B,B,N,B,B],[B,N,N,N,B],[N,N,N,N,N],[B,N,N,N,B],[B,B,N,B,B]]
Step4 = [[B,N,N,N,B],[N,N,N,N,N],[N,N,N,N,N],[N,N,N,N,N],[B,N,N,N,B]]
for y in range(h/5):
for x in range(w/5):
media = 0
for y2 in range(5):
for x2 in range(5):
media += matrice[y*5+y2][x*5+x2]
media = media /25
for y3 in range(5):
for x3 in range(5):
if media >= 250 and media <= 255:
matrice_BN[y*5+y3][x*5+x3] = B
if media >= 190 and media < 250:
matrice_BN[y*5+y3][x*5+x3] = Step1[y3][x3]
if media >= 130 and media < 190:
matrice_BN[y*5+y3][x*5+x3] = Step2[y3][x3]
if media >= 70 and media < 130:
matrice_BN[y*5+y3][x*5+x3] = Step3[y3][x3]
if media >= 10 and media < 70:
matrice_BN[y*5+y3][x*5+x3] = Step4[y3][x3]
if media >= 0 and media < 10:
matrice_BN[y*5+y3][x*5+x3] = N
elif self.options.conversion_type == 4:
#Halftone row
Step1r = [B,B,N,B,B]
Step2r = [B,N,N,B,B]
Step3r = [B,N,N,N,B]
Step4r = [N,N,N,N,B]
for y in range(h):
for x in range(w/5):
media = 0
for x2 in range(5):
media += matrice[y][x*5+x2]
media = media /5
for x3 in range(5):
if media >= 250 and media <= 255:
matrice_BN[y][x*5+x3] = B
if media >= 190 and media < 250:
matrice_BN[y][x*5+x3] = Step1r[x3]
if media >= 130 and media < 190:
matrice_BN[y][x*5+x3] = Step2r[x3]
if media >= 70 and media < 130:
matrice_BN[y][x*5+x3] = Step3r[x3]
if media >= 10 and media < 70:
matrice_BN[y][x*5+x3] = Step4r[x3]
if media >= 0 and media < 10:
matrice_BN[y][x*5+x3] = N
elif self.options.conversion_type == 5:
#Halftone column
Step1c = [B,B,N,B,B]
Step2c = [B,N,N,B,B]
Step3c = [B,N,N,N,B]
Step4c = [N,N,N,N,B]
for y in range(h/5):
for x in range(w):
media = 0
for y2 in range(5):
media += matrice[y*5+y2][x]
media = media /5
for y3 in range(5):
if media >= 250 and media <= 255:
matrice_BN[y*5+y3][x] = B
if media >= 190 and media < 250:
matrice_BN[y*5+y3][x] = Step1c[y3]
if media >= 130 and media < 190:
matrice_BN[y*5+y3][x] = Step2c[y3]
if media >= 70 and media < 130:
matrice_BN[y*5+y3][x] = Step3c[y3]
if media >= 10 and media < 70:
matrice_BN[y*5+y3][x] = Step4c[y3]
if media >= 0 and media < 10:
matrice_BN[y*5+y3][x] = N
else:
#Grayscale
if self.options.grayscale_resolution == 1:
matrice_BN = matrice
else:
for y in range(h):
for x in range(w):
if matrice[y][x] <= 1:
matrice_BN[y][x] == 0
if matrice[y][x] >= 254:
matrice_BN[y][x] == 255
if matrice[y][x] > 1 and matrice[y][x] <254:
matrice_BN[y][x] = ( matrice[y][x] // self.options.grayscale_resolution ) * self.options.grayscale_resolution
####Ora matrice_BN contiene l'immagine in Bianco (255) e Nero (0)
#### SAVE BLACK AND BLACK IMAGE ####
file_img_BN = open(pos_file_png_BW, 'wb') #Create the file
Costruttore_img = fablabchemnitz_png.Writer(w, h, greyscale=True, bitdepth=8) #Setting the image file
Costruttore_img.write(file_img_BN, matrice_BN) #Image file builder
file_img_BN.close() #Close the file
#### GENERO IL FILE GCODE ####
if self.options.preview_only == False: #Genero Gcode solo se devo
if self.options.flip_y == False: #Inverto asse Y solo se flip_y = False
#-> coordinate Cartesiane (False) Coordinate "informatiche" (True)
matrice_BN.reverse()
Laser_ON = False
F_G01 = self.options.speed_ON
Scala = self.options.resolution
Scaler = float(self.options.BW_Max)/255
file_gcode = open(pos_file_gcode, 'w') #Create the file
#Configurazioni iniziali standard Gcode
file_gcode.write('; Generated with:\n; "Raster 2 Laser Gcode generator"\n; by 305 Engineering\n; With a remix by VE7FRG\n;\n;\n')
#HOMING
file_gcode.write('G21; Set units to millimeters\n')
file_gcode.write('G90; Use absolute coordinates\n')
file_gcode.write('G92; Coordinate Offset\n')
if self.options.homing == 1:
file_gcode.write('G28; home all axes\n')
file_gcode.write('M42 P44 S0; Turn on LEDs\n')
file_gcode.write('M42 P64 S0; Turn on VENT Fans\n')
elif self.options.homing == 2:
file_gcode.write('$H; home all axes\n')
elif self.options.homing == 4:
file_gcode.write('G28 X0 Y0; home all axes\n')
file_gcode.write('G92 X-47 Y-27; Coordinate Offset for CR-10 Mini\n')
file_gcode.write('G0 Z100; Set laser head 100mm above surface\n')
else:
pass
# file_gcode.write('G90; Use absolute coordinates\n')
# file_gcode.write('G92; Coordinate Offset\n')
#Creazione del Gcode
#allargo la matrice per lavorare su tutta l'immagine
for y in range(h):
matrice_BN[y].append(B)
w = w+1
if self.options.conversion_type != 6:
for y in range(h):
if y % 2 == 0 :
for x in range(w):
if matrice_BN[y][x] == N :
if Laser_ON == False :
#file_gcode.write('G00 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G00) + '\n')
file_gcode.write('G00 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + '\n') #tolto il Feed sul G00
file_gcode.write(self.options.laseron + '\n')
Laser_ON = True
if Laser_ON == True : #DEVO evitare di uscire dalla matrice
if x == w-1 :
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) +' F' + str(F_G01) + '\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
else:
if matrice_BN[y][x+1] != N :
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G01) +'\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
else:
for x in reversed(range(w)):
if matrice_BN[y][x] == N :
if Laser_ON == False :
#file_gcode.write('G00 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G00) + '\n')
file_gcode.write('G00 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + '\n') #tolto il Feed sul G00
file_gcode.write(self.options.laseron + '\n')
Laser_ON = True
if Laser_ON == True : #DEVO evitare di uscire dalla matrice
if x == 0 :
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) +' F' + str(F_G01) + '\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
else:
if matrice_BN[y][x-1] != N :
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G01) +'\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
else: ##SCALA DI GRIGI
for y in range(h):
if y % 2 == 0 :
for x in range(w):
if matrice_BN[y][x] != B :
if Laser_ON == False :
file_gcode.write('G00 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) +'\n')
file_gcode.write(self.options.laseron + ' '+ ' S' + str(int(round(float((255 - matrice_BN[y][x])*Scaler)))) +'\n')
Laser_ON = True
if Laser_ON == True : #DEVO evitare di uscire dalla matrice
if x == w-1 : #controllo fine riga
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) +' F' + str(F_G01) + '\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
else:
if matrice_BN[y][x+1] == B :
file_gcode.write('G1 X' + str(float(x+1)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G01) +'\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
elif matrice_BN[y][x] != matrice_BN[y][x+1] :
file_gcode.write('G1 X' + str(float(x+1)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G01) +'\n')
file_gcode.write(self.options.laseron + ' '+ ' S' + str(int(round(float((255 - matrice_BN[y][x])*Scaler)))) +'\n')
else:
for x in reversed(range(w)):
if matrice_BN[y][x] != B :
if Laser_ON == False :
file_gcode.write('G00 X' + str(float(x+1)/Scala) + ' Y' + str(float(y)/Scala) +'\n')
#file_gcode.write(self.options.laseron + ' '+ ' S' + str(self.options.BW_Max - matrice_BN[y][x]) +'\n')
file_gcode.write(self.options.laseron + ' '+ ' S' + str(int(round(float((255 - matrice_BN[y][x])*Scaler)))) +'\n')
Laser_ON = True
if Laser_ON == True : #DEVO evitare di uscire dalla matrice
if x == 0 : #controllo fine riga ritorno
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) +' F' + str(F_G01) + '\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
else:
if matrice_BN[y][x-1] == B :
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G01) +'\n')
file_gcode.write(self.options.laseroff + '\n')
Laser_ON = False
elif matrice_BN[y][x] != matrice_BN[y][x-1] :
file_gcode.write('G1 X' + str(float(x)/Scala) + ' Y' + str(float(y)/Scala) + ' F' + str(F_G01) +'\n')
#file_gcode.write(self.options.laseron + ' '+ ' S' + str(self.options.BW_Max - matrice_BN[y][x-1]) +'\n')
file_gcode.write(self.options.laseron + ' '+ ' S' + str(int(round(float((255 - matrice_BN[y][x])*Scaler)))) +'\n')
#Configurazioni finali standard Gcode
file_gcode.write('G00 X0 Y0; home\n')
#HOMING
if self.options.homing == 1:
file_gcode.write('G28 X0 Y0; home all axes\n')
file_gcode.write('M42 P44 S255; Turn on LEDs\n')
file_gcode.write('M42 P64 S255; Turn on VENT Fans\n')
elif self.options.homing == 2:
file_gcode.write('$H; home all axes\n')
else:
pass
file_gcode.close() #Chiudo il file
######## ######## ######## ######## ######## ######## ######## ######## ########
def _main():
e=GcodeExport()
e.affect()
exit()
if __name__=="__main__":
_main()