Merge pull request #264 from iXce/experimental
Build system and CLI switch to request webinterfacemaster
commit
7e2e6a519f
3075
20cube_export.gcode
3075
20cube_export.gcode
File diff suppressed because it is too large
Load Diff
15
plater.py
15
plater.py
|
@ -17,12 +17,10 @@
|
|||
|
||||
# Set up Internationalization using gettext
|
||||
# searching for installed locales on /usr/share; uses relative folder if not found (windows)
|
||||
import os, gettext, Queue, re
|
||||
import os, Queue, re
|
||||
|
||||
if os.path.exists('/usr/share/pronterface/locale'):
|
||||
gettext.install('plater', '/usr/share/pronterface/locale', unicode=1)
|
||||
else:
|
||||
gettext.install('plater', './locale', unicode=1)
|
||||
from printrun.printrun_utils import install_locale
|
||||
install_locale('plater')
|
||||
|
||||
import wx
|
||||
import time
|
||||
|
@ -31,12 +29,13 @@ import threading
|
|||
import math
|
||||
import sys
|
||||
|
||||
import stltool
|
||||
from printrun import stltool
|
||||
from printrun.printrun_utils import pixmapfile
|
||||
|
||||
glview = False
|
||||
if "-nogl" not in sys.argv:
|
||||
try:
|
||||
import stlview
|
||||
from printrun import stlview
|
||||
glview = True
|
||||
except:
|
||||
pass
|
||||
|
@ -245,7 +244,7 @@ class showstl(wx.Window):
|
|||
class stlwin(wx.Frame):
|
||||
def __init__(self, size=(800, 580), callback=None, parent=None):
|
||||
wx.Frame.__init__(self, parent, title=_("Plate building tool"), size=size)
|
||||
self.SetIcon(wx.Icon("plater.ico", wx.BITMAP_TYPE_ICO))
|
||||
self.SetIcon(wx.Icon(pixmapfile("plater.ico"), wx.BITMAP_TYPE_ICO))
|
||||
self.mainsizer = wx.BoxSizer(wx.HORIZONTAL)
|
||||
self.panel = wx.Panel(self, -1, size=(150, 600), pos=(0, 0))
|
||||
#self.panel.SetBackgroundColour((10, 10, 10))
|
||||
|
|
|
@ -13,6 +13,9 @@
|
|||
# You should have received a copy of the GNU General Public License
|
||||
# along with Printrun. If not, see <http://www.gnu.org/licenses/>.
|
||||
import wx,time
|
||||
|
||||
from printrun_utils import imagefile
|
||||
|
||||
ID_ABOUT = 101
|
||||
ID_EXIT = 110
|
||||
class window(wx.Frame):
|
||||
|
@ -22,11 +25,11 @@ class window(wx.Frame):
|
|||
|
||||
vbox = wx.BoxSizer(wx.VERTICAL)
|
||||
toolbar = wx.ToolBar(self, -1, style=wx.TB_HORIZONTAL | wx.NO_BORDER)
|
||||
toolbar.AddSimpleTool(1, wx.Image('./images/zoom_in.png', wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Zoom In [+]', '')
|
||||
toolbar.AddSimpleTool(2, wx.Image('./images/zoom_out.png', wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Zoom Out [-]', '')
|
||||
toolbar.AddSimpleTool(1, wx.Image(imagefile('zoom_in.png'), wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Zoom In [+]', '')
|
||||
toolbar.AddSimpleTool(2, wx.Image(imagefile('zoom_out.png'), wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Zoom Out [-]', '')
|
||||
toolbar.AddSeparator()
|
||||
toolbar.AddSimpleTool(3, wx.Image('./images/arrow_up.png', wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Move Up a Layer [U]', '')
|
||||
toolbar.AddSimpleTool(4, wx.Image('./images/arrow_down.png', wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Move Down a Layer [D]', '')
|
||||
toolbar.AddSimpleTool(3, wx.Image(imagefile('arrow_up.png'), wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Move Up a Layer [U]', '')
|
||||
toolbar.AddSimpleTool(4, wx.Image(imagefile('arrow_down.png'), wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Move Down a Layer [D]', '')
|
||||
toolbar.AddSimpleTool(5, wx.EmptyBitmap(16,16), 'Reset view', '')
|
||||
toolbar.AddSeparator()
|
||||
#toolbar.AddSimpleTool(5, wx.Image('./images/inject.png', wx.BITMAP_TYPE_PNG).ConvertToBitmap(), 'Insert Code at start of this layer', '')
|
|
@ -0,0 +1,37 @@
|
|||
import os
|
||||
import gettext
|
||||
|
||||
def install_locale(domain):
|
||||
if os.path.exists('/usr/share/pronterface/locale'):
|
||||
gettext.install(domain, '/usr/share/pronterface/locale', unicode=1)
|
||||
elif os.path.exists('/usr/local/share/pronterface/locale'):
|
||||
gettext.install(domain, '/usr/local/share/pronterface/locale', unicode=1)
|
||||
else:
|
||||
gettext.install(domain, './locale', unicode=1)
|
||||
|
||||
def imagefile(filename):
|
||||
for prefix in ['/usr/local/share/pronterface/images', '/usr/share/pronterface/images']:
|
||||
candidate = os.path.join(prefix, filename)
|
||||
if os.path.exists(candidate):
|
||||
return candidate
|
||||
local_candidate = os.path.join(os.path.dirname(__file__), "images", filename)
|
||||
if os.path.exists(local_candidate):
|
||||
return local_candidate
|
||||
else:
|
||||
return os.path.join(os.path.split(os.path.split(__file__)[0])[0], "images", filename)
|
||||
|
||||
def lookup_file(filename, prefixes):
|
||||
for prefix in prefixes:
|
||||
candidate = os.path.join(prefix, filename)
|
||||
if os.path.exists(candidate):
|
||||
return candidate
|
||||
return filename
|
||||
|
||||
def pixmapfile(filename):
|
||||
return lookup_file(filename, ['/usr/local/share/pixmaps', '/usr/share/pixmaps'])
|
||||
|
||||
def sharedfile(filename):
|
||||
return lookup_file(filename, ['/usr/local/share/pronterface', '/usr/share/pronterface'])
|
||||
|
||||
def configfile(filename):
|
||||
return lookup_file(filename, [os.path.expanduser("~/.printrun/"),])
|
|
@ -1,7 +1,10 @@
|
|||
#!/usr/bin/python
|
||||
import cherrypy, pronterface, re, ConfigParser, threading, sys
|
||||
import pronterface
|
||||
import cherrypy, re, ConfigParser, threading, sys
|
||||
import os.path
|
||||
|
||||
from printrun.printrun_utils import configfile, imagefile, sharedfile
|
||||
|
||||
users = {}
|
||||
|
||||
def PrintHeader():
|
||||
|
@ -238,7 +241,7 @@ class WebInterface(object):
|
|||
config = ConfigParser.SafeConfigParser(allow_no_value=True)
|
||||
else:
|
||||
config = ConfigParser.SafeConfigParser()
|
||||
config.read('auth.config')
|
||||
config.read(configfile(pface.web_auth_config or 'auth.config'))
|
||||
users[config.get("user", "user")] = config.get("user", "pass")
|
||||
self.pface = pface
|
||||
global gPronterPtr
|
||||
|
@ -358,19 +361,19 @@ def KillWebInterfaceThread():
|
|||
def StartWebInterfaceThread(webInterface):
|
||||
current_dir = os.path.dirname(os.path.abspath(__file__))
|
||||
cherrypy.config.update({'engine.autoreload_on':False})
|
||||
cherrypy.config.update("http.config")
|
||||
cherrypy.config.update(configfile(webInterface.pface.web_config or "http.config"))
|
||||
conf = {'/css/style.css': {'tools.staticfile.on': True,
|
||||
'tools.staticfile.filename': os.path.join(current_dir, 'css/style.css'),
|
||||
'tools.staticfile.filename': sharedfile('css/style.css'),
|
||||
},
|
||||
'/images/control_xy.png': {'tools.staticfile.on': True,
|
||||
'tools.staticfile.filename': os.path.join(current_dir, 'images/control_xy.png'),
|
||||
'tools.staticfile.filename': imagefile('control_xy.png'),
|
||||
},
|
||||
'/images/control_z.png': {'tools.staticfile.on': True,
|
||||
'tools.staticfile.filename': os.path.join(current_dir, 'images/control_z.png'),
|
||||
'tools.staticfile.filename': imagefile('control_z.png'),
|
||||
}}
|
||||
cherrypy.config.update("http.config")
|
||||
cherrypy.config.update(configfile(webInterface.pface.web_config or "http.config"))
|
||||
cherrypy.quickstart(webInterface, '/', config=conf)
|
||||
|
||||
if __name__ == '__main__':
|
||||
cherrypy.config.update("http.config")
|
||||
cherrypy.config.update(configfile("http.config"))
|
||||
cherrypy.quickstart(WebInterfaceStub())
|
|
@ -15,14 +15,8 @@
|
|||
|
||||
import wx, os, math
|
||||
from bufferedcanvas import *
|
||||
from printrun_utils import *
|
||||
|
||||
|
||||
def imagefile(filename):
|
||||
if os.path.exists(os.path.join(os.path.dirname(__file__), "images", filename)):
|
||||
return os.path.join(os.path.dirname(__file__), "images", filename)
|
||||
else:
|
||||
return os.path.join(os.path.split(os.path.split(__file__)[0])[0], "images", filename)
|
||||
|
||||
def sign(n):
|
||||
if n < 0: return -1
|
||||
elif n > 0: return 1
|
|
@ -15,14 +15,7 @@
|
|||
|
||||
import wx, os, math
|
||||
from bufferedcanvas import *
|
||||
|
||||
def imagefile(filename):
|
||||
if os.path.exists(os.path.join(os.path.dirname(__file__), "images", filename)):
|
||||
return os.path.join(os.path.dirname(__file__), "images", filename)
|
||||
else:
|
||||
return os.path.join(os.path.split(os.path.split(__file__)[0])[0], "images", filename)
|
||||
|
||||
|
||||
from printrun_utils import *
|
||||
|
||||
def sign(n):
|
||||
if n < 0: return -1
|
22
pronsole.py
22
pronsole.py
|
@ -15,16 +15,15 @@
|
|||
# You should have received a copy of the GNU General Public License
|
||||
# along with Printrun. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import cmd, printcore, sys
|
||||
import cmd, sys
|
||||
import glob, os, time
|
||||
import sys, subprocess
|
||||
import math, codecs
|
||||
from math import sqrt
|
||||
import gettext
|
||||
if os.path.exists('/usr/share/pronterface/locale'):
|
||||
gettext.install('pronterface', '/usr/share/pronterface/locale', unicode=1)
|
||||
else:
|
||||
gettext.install('pronterface', './locale', unicode=1)
|
||||
|
||||
from printrun import printcore
|
||||
from printrun.printrun_utils import install_locale
|
||||
install_locale('pronterface')
|
||||
|
||||
if os.name=="nt":
|
||||
try:
|
||||
|
@ -277,6 +276,9 @@ class pronsole(cmd.Cmd):
|
|||
self.helpdict["z_feedrate"] = _("Feedrate for Control Panel Moves in Z (default: 200mm/min)")
|
||||
self.helpdict["final_command"] = _("Executable to run when the print is finished")
|
||||
self.commandprefixes='MGT$'
|
||||
self.webrequested=False
|
||||
self.web_config=None
|
||||
self.web_auth_config=None
|
||||
|
||||
def set_temp_preset(self,key,value):
|
||||
if not key.startswith("bed"):
|
||||
|
@ -1216,11 +1218,17 @@ class pronsole(cmd.Cmd):
|
|||
|
||||
def parse_cmdline(self,args):
|
||||
import getopt
|
||||
opts,args = getopt.getopt(args, "c:e:h", ["conf=","config=","help"])
|
||||
opts,args = getopt.getopt(args, "c:e:hw", ["conf=","config=","help","web","web-config=", "web-auth-config="])
|
||||
for o,a in opts:
|
||||
#print repr((o,a))
|
||||
if o in ("-c","--conf","--config"):
|
||||
self.load_rc(a)
|
||||
elif o in ("-w","--web"):
|
||||
self.webrequested = True
|
||||
elif o == "--web-config":
|
||||
self.web_config = a
|
||||
elif o == "--web-auth-config":
|
||||
self.web_auth_config = a
|
||||
elif o in ("-h","--help"):
|
||||
print "Usage: "+sys.argv[0]+' [-c filename [-c filename2 ... ] ] [-e "command" ...]'
|
||||
print " -c | --conf | --config - override startup .pronsolerc file"
|
||||
|
|
149
pronterface.py
149
pronterface.py
|
@ -17,23 +17,18 @@
|
|||
|
||||
# Set up Internationalization using gettext
|
||||
# searching for installed locales on /usr/share; uses relative folder if not found (windows)
|
||||
import os, gettext, Queue, re
|
||||
import os, Queue, re
|
||||
|
||||
if os.path.exists('/usr/share/pronterface/locale'):
|
||||
gettext.install('pronterface', '/usr/share/pronterface/locale', unicode=1)
|
||||
else:
|
||||
gettext.install('pronterface', './locale', unicode=1)
|
||||
from printrun.printrun_utils import install_locale
|
||||
install_locale('pronterface')
|
||||
|
||||
try:
|
||||
import wx
|
||||
except:
|
||||
print _("WX is not installed. This program requires WX to run.")
|
||||
raise
|
||||
import printcore, sys, glob, time, threading, traceback, gviz, traceback, cStringIO, subprocess
|
||||
try:
|
||||
os.chdir(os.path.split(__file__)[0])
|
||||
except:
|
||||
pass
|
||||
import sys, glob, time, threading, traceback, cStringIO, subprocess
|
||||
|
||||
StringIO=cStringIO
|
||||
|
||||
thread=threading.Thread
|
||||
|
@ -49,24 +44,19 @@ if os.name=="nt":
|
|||
pass
|
||||
|
||||
|
||||
|
||||
from xybuttons import XYButtons
|
||||
from zbuttons import ZButtons
|
||||
from graph import Graph
|
||||
from printrun import printcore, gviz
|
||||
from printrun.xybuttons import XYButtons
|
||||
from printrun.zbuttons import ZButtons
|
||||
from printrun.graph import Graph
|
||||
from printrun.printrun_utils import pixmapfile, configfile
|
||||
import pronsole
|
||||
|
||||
webavail = False
|
||||
try :
|
||||
if webavail:
|
||||
import cherrypy, webinterface
|
||||
from threading import Thread
|
||||
except:
|
||||
print _("CherryPy is not installed. Web Interface Disabled.")
|
||||
webavail = False
|
||||
|
||||
|
||||
def dosify(name):
|
||||
return os.path.split(name)[1].split(".")[0][:8]+".g"
|
||||
|
||||
def parse_temperature_report(report, key):
|
||||
return float(filter(lambda x: x.startswith(key), report.split())[0].split(":")[1].split("/")[0])
|
||||
|
||||
class Tee(object):
|
||||
def __init__(self, target):
|
||||
self.stdout = sys.stdout
|
||||
|
@ -106,7 +96,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.filename=filename
|
||||
os.putenv("UBUNTU_MENUPROXY","0")
|
||||
wx.Frame.__init__(self,None,title=_("Printer Interface"),size=size);
|
||||
self.SetIcon(wx.Icon("P-face.ico",wx.BITMAP_TYPE_ICO))
|
||||
self.SetIcon(wx.Icon(pixmapfile("P-face.ico"),wx.BITMAP_TYPE_ICO))
|
||||
self.panel=wx.Panel(self,-1,size=size)
|
||||
|
||||
self.statuscheck=False
|
||||
|
@ -135,7 +125,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.panel.SetBackgroundColour(self.settings.bgcolor)
|
||||
customdict={}
|
||||
try:
|
||||
execfile("custombtn.txt",customdict)
|
||||
execfile(configfile("custombtn.txt"),customdict)
|
||||
if len(customdict["btns"]):
|
||||
if not len(self.custombuttons):
|
||||
try:
|
||||
|
@ -169,11 +159,22 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.cur_button=None
|
||||
self.hsetpoint=0.0
|
||||
self.bsetpoint=0.0
|
||||
if webavail:
|
||||
self.webInterface=webinterface.WebInterface(self)
|
||||
self.webThread = Thread(target=webinterface.StartWebInterfaceThread, args=(self.webInterface, ))
|
||||
self.webThread.start()
|
||||
if(self.filename is not None):
|
||||
self.webInterface=None
|
||||
if self.webrequested:
|
||||
try :
|
||||
import cherrypy
|
||||
from printrun import webinterface
|
||||
except:
|
||||
print _("CherryPy is not installed. Web Interface Disabled.")
|
||||
try:
|
||||
self.webInterface=webinterface.WebInterface(self)
|
||||
self.webThread=threading.Thread(target=webinterface.StartWebInterfaceThread, args=(self.webInterface, ))
|
||||
self.webThread.start()
|
||||
except:
|
||||
print _("Failed to start web interface")
|
||||
traceback.print_exc(file = sys.stdout)
|
||||
self.webInterface = None
|
||||
if self.filename is not None:
|
||||
self.do_load(self.filename)
|
||||
|
||||
def startcb(self):
|
||||
|
@ -272,7 +273,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
#self.bedtgauge.SetTarget(int(f))
|
||||
wx.CallAfter(self.graph.SetBedTargetTemperature,int(f))
|
||||
if f>0:
|
||||
wx.CallAfter(self.btemp.SetValue,l)
|
||||
wx.CallAfter(self.btemp.SetValue,str(f))
|
||||
self.set("last_bed_temperature",str(f))
|
||||
wx.CallAfter(self.setboff.SetBackgroundColour,"")
|
||||
wx.CallAfter(self.setboff.SetForegroundColour,"")
|
||||
|
@ -292,7 +293,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
#self.hottgauge.SetTarget(int(f))
|
||||
wx.CallAfter(self.graph.SetExtruder0TargetTemperature,int(f))
|
||||
if f>0:
|
||||
wx.CallAfter(self.htemp.SetValue,l)
|
||||
wx.CallAfter(self.htemp.SetValue,str(f))
|
||||
self.set("last_temperature",str(f))
|
||||
wx.CallAfter(self.settoff.SetBackgroundColour,"")
|
||||
wx.CallAfter(self.settoff.SetForegroundColour,"")
|
||||
|
@ -309,7 +310,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
|
||||
def do_settemp(self,l=""):
|
||||
try:
|
||||
if not (l.__class__=="".__class__ or l.__class__==u"".__class__) or (not len(l)):
|
||||
if not (l.__class__=="".__class__ or l.__class__==u"".__class__) or not l:
|
||||
l=str(self.htemp.GetValue().split()[0])
|
||||
l=l.lower().replace(",",".")
|
||||
for i in self.temps.keys():
|
||||
|
@ -326,7 +327,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
print _("You cannot set negative temperatures. To turn the hotend off entirely, set its temperature to 0.")
|
||||
except Exception,x:
|
||||
print _("You must enter a temperature. (%s)" % (repr(x),))
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("You must enter a temperature. (%s)" % (repr(x),))
|
||||
|
||||
def do_bedtemp(self,l=""):
|
||||
|
@ -344,15 +345,15 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.setbedgui(f)
|
||||
else:
|
||||
print _("Printer is not online.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Printer is not online.")
|
||||
else:
|
||||
print _("You cannot set negative temperatures. To turn the bed off entirely, set its temperature to 0.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("You cannot set negative temperatures. To turn the bed off entirely, set its temperature to 0.")
|
||||
except:
|
||||
print _("You must enter a temperature.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("You must enter a temperature.")
|
||||
|
||||
def end_macro(self):
|
||||
|
@ -373,7 +374,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.delete_macro(macro_name)
|
||||
return
|
||||
print _("Cancelled.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Cancelled.")
|
||||
return
|
||||
self.cur_macro_name = macro_name
|
||||
|
@ -393,7 +394,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.capture_skip_newline = True
|
||||
return
|
||||
wx.CallAfter(self.addtexttolog,l);
|
||||
|
||||
|
||||
def scanserial(self):
|
||||
"""scan for available ports. return a list of device names."""
|
||||
baselist=[]
|
||||
|
@ -409,12 +410,12 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
return baselist+glob.glob('/dev/ttyUSB*') + glob.glob('/dev/ttyACM*') +glob.glob("/dev/tty.*")+glob.glob("/dev/cu.*")+glob.glob("/dev/rfcomm*")
|
||||
|
||||
def project(self,event):
|
||||
import projectlayer
|
||||
from printrun import projectlayer
|
||||
if(self.p.online):
|
||||
projectlayer.setframe(self,self.p).Show()
|
||||
else:
|
||||
print _("Printer is not online.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Printer is not online.")
|
||||
|
||||
def popmenu(self):
|
||||
|
@ -493,7 +494,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
old_def = self.macros[macro]
|
||||
elif len([c for c in macro.encode("ascii","replace") if not c.isalnum() and c != "_"]):
|
||||
print _("Macro name may contain only ASCII alphanumeric symbols and underscores")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Macro name may contain only alphanumeric symbols and underscores")
|
||||
return
|
||||
elif hasattr(self.__class__,"do_"+macro):
|
||||
|
@ -793,7 +794,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.gviz.showall=1
|
||||
try:
|
||||
raise ""
|
||||
import stlview
|
||||
from printrun import stlview
|
||||
self.gwindow=stlview.GCFrame(None, wx.ID_ANY, 'Gcode view, shift to move view, mousewheel to set layer', size=(600,600))
|
||||
except:
|
||||
self.gwindow=gviz.window([],
|
||||
|
@ -979,7 +980,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
|
||||
def help_button(self):
|
||||
print _('Defines custom button. Usage: button <num> "title" [/c "colour"] command')
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog('Defines custom button. Usage: button <num> "title" [/c "colour"] command')
|
||||
|
||||
def do_button(self,argstr):
|
||||
|
@ -1003,7 +1004,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
command=argstr.strip()
|
||||
if num<0 or num>=64:
|
||||
print _("Custom button number should be between 0 and 63")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Custom button number should be between 0 and 63")
|
||||
return
|
||||
while num >= len(self.custombuttons):
|
||||
|
@ -1271,7 +1272,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.cur_button=None
|
||||
except:
|
||||
print _("event object missing")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("event object missing")
|
||||
self.cur_button=None
|
||||
raise
|
||||
|
@ -1289,7 +1290,8 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
except:
|
||||
pass
|
||||
self.Destroy()
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
from printrun import webinterface
|
||||
webinterface.KillWebInterfaceThread()
|
||||
|
||||
def do_monitor(self,l=""):
|
||||
|
@ -1303,16 +1305,16 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
wx.CallAfter(self.monitorbox.SetValue,self.monitor_interval>0)
|
||||
except:
|
||||
print _("Invalid period given.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Invalid period given.")
|
||||
self.setmonitor(None)
|
||||
if self.monitor:
|
||||
print _("Monitoring printer.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Monitoring printer.")
|
||||
else:
|
||||
print _("Done monitoring.")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Done monitoring.")
|
||||
|
||||
|
||||
|
@ -1329,7 +1331,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
except:
|
||||
print "attempted to write invalid text to console"
|
||||
pass
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AppendLog(text)
|
||||
|
||||
def setloud(self,e):
|
||||
|
@ -1361,10 +1363,10 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
#string+=(self.tempreport.replace("\r","").replace("T:",_("Hotend") + ":").replace("B:",_("Bed") + ":").replace("\n","").replace("ok ",""))+" "
|
||||
wx.CallAfter(self.tempdisp.SetLabel,self.tempreport.strip().replace("ok ",""))
|
||||
try:
|
||||
#self.hottgauge.SetValue(float(filter(lambda x:x.startswith("T:"),self.tempreport.split())[0].split(":")[1]))
|
||||
wx.CallAfter(self.graph.SetExtruder0Temperature,float(filter(lambda x:x.startswith("T:"),self.tempreport.split())[0].split(":")[1]))
|
||||
#self.bedtgauge.SetValue(float(filter(lambda x:x.startswith("B:"),self.tempreport.split())[0].split(":")[1]))
|
||||
wx.CallAfter(self.graph.SetBedTemperature,float(filter(lambda x:x.startswith("B:"),self.tempreport.split())[0].split(":")[1]))
|
||||
#self.hottgauge.SetValue(parse_temperature_report(self.tempreport, "T:"))
|
||||
wx.CallAfter(self.graph.SetExtruder0Temperature, parse_temperature_report(self.tempreport, "T:"))
|
||||
#self.bedtgauge.SetValue(parse_temperature_report(self.tempreport, "B:"))
|
||||
wx.CallAfter(self.graph.SetBedTemperature, parse_temperature_report(self.tempreport, "B:"))
|
||||
except:
|
||||
pass
|
||||
fractioncomplete = 0.0
|
||||
|
@ -1401,6 +1403,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
wx.CallAfter(self.status.SetStatusText,_("Not connected to printer."))
|
||||
except:
|
||||
pass #if window has been closed
|
||||
|
||||
def capture(self, func, *args, **kwargs):
|
||||
stdout=sys.stdout
|
||||
cout=None
|
||||
|
@ -1425,11 +1428,11 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.tempreport=l
|
||||
wx.CallAfter(self.tempdisp.SetLabel,self.tempreport.strip().replace("ok ",""))
|
||||
try:
|
||||
#self.hottgauge.SetValue(float(filter(lambda x:x.startswith("T:"),self.tempreport.split())[0].split(":")[1]))
|
||||
wx.CallAfter(self.graph.SetExtruder0Temperature,float(filter(lambda x:x.startswith("T:"),self.tempreport.split())[0].split(":")[1]))
|
||||
wx.CallAfter(self.graph.SetBedTemperature,float(filter(lambda x:x.startswith("B:"),self.tempreport.split())[0].split(":")[1]))
|
||||
#self.hottgauge.SetValue(parse_temperature_report(self.tempreport, "T:"))
|
||||
wx.CallAfter(self.graph.SetExtruder0Temperature, parse_temperature_report(self.tempreport, "T:"))
|
||||
wx.CallAfter(self.graph.SetBedTemperature, parse_temperature_report(self.tempreport, "B:"))
|
||||
except:
|
||||
pass
|
||||
traceback.print_exc()
|
||||
tstring=l.rstrip()
|
||||
#print tstring
|
||||
if (tstring!="ok") and (tstring!="wait") and ("ok T:" not in tstring) and (not self.p.loud):
|
||||
|
@ -1477,8 +1480,6 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
except:
|
||||
pass
|
||||
|
||||
|
||||
|
||||
def filesloaded(self):
|
||||
dlg=wx.SingleChoiceDialog(self, _("Select the file to print"), _("Pick SD file"), self.sdfiles)
|
||||
if(dlg.ShowModal()==wx.ID_OK):
|
||||
|
@ -1486,9 +1487,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
if len(target):
|
||||
self.recvlisteners+=[self.waitforsdresponse]
|
||||
self.p.send_now("M23 "+target.lower())
|
||||
|
||||
#print self.sdfiles
|
||||
pass
|
||||
|
||||
def getfiles(self):
|
||||
if not self.p.online:
|
||||
|
@ -1505,7 +1504,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
import shlex
|
||||
param = self.expandcommand(self.settings.slicecommand).encode()
|
||||
print "Slicing: ",param
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Slicing: "+param)
|
||||
pararray=[i.replace("$s",self.filename).replace("$o",self.filename.replace(".stl","_export.gcode").replace(".STL","_export.gcode")).encode() for i in shlex.split(param.replace("\\","\\\\").encode())]
|
||||
#print pararray
|
||||
|
@ -1518,7 +1517,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.stopsf=1
|
||||
except:
|
||||
print _("Failed to execute slicing software: ")
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog("Failed to execute slicing software: ")
|
||||
self.stopsf=1
|
||||
traceback.print_exc(file=sys.stdout)
|
||||
|
@ -1550,7 +1549,6 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.skeining=0
|
||||
self.skeinp=None
|
||||
|
||||
|
||||
def skein(self,filename):
|
||||
wx.CallAfter(self.loadbtn.SetLabel,_("Cancel"))
|
||||
print _("Slicing ") + filename
|
||||
|
@ -1612,7 +1610,7 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
Xtot,Ytot,Ztot,Xmin,Xmax,Ymin,Ymax,Zmin,Zmax = pronsole.measurements(self.f)
|
||||
print pronsole.totalelength(self.f), _("mm of filament used in this print\n")
|
||||
print _("the print goes from %f mm to %f mm in X\nand is %f mm wide\n") % (Xmin, Xmax, Xtot)
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
self.webInterface.AddLog(_("the print goes from %f mm to %f mm in X\nand is %f mm wide\n") % (Xmin, Xmax, Xtot))
|
||||
print _("the print goes from %f mm to %f mm in Y\nand is %f mm wide\n") % (Ymin, Ymax, Ytot)
|
||||
print _("the print goes from %f mm to %f mm in Z\nand is %f mm high\n") % (Zmin, Zmax, Ztot)
|
||||
|
@ -1706,7 +1704,6 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.p.resume()
|
||||
wx.CallAfter(self.pausebtn.SetLabel, _("Pause"))
|
||||
|
||||
|
||||
def sdprintfile(self,event):
|
||||
self.on_startprint()
|
||||
threading.Thread(target=self.getfiles).start()
|
||||
|
@ -1742,7 +1739,6 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
self.set("baudrate",str(baud))
|
||||
threading.Thread(target=self.statuschecker).start()
|
||||
|
||||
|
||||
def disconnect(self,event):
|
||||
print _("Disconnected.")
|
||||
self.p.disconnect()
|
||||
|
@ -1770,7 +1766,6 @@ class PronterWindow(wx.Frame,pronsole.pronsole):
|
|||
if self.sdprinting:
|
||||
self.p.send_now("M26 S0")
|
||||
|
||||
|
||||
def reset(self,event):
|
||||
print _("Reset.")
|
||||
dlg=wx.MessageDialog(self, _("Are you sure you want to reset the printer?"), _("Reset?"), wx.YES|wx.NO)
|
||||
|
@ -1858,8 +1853,6 @@ class macroed(wx.Dialog):
|
|||
if position == -1 :
|
||||
# ShowMessage(self,-1, "Not found!")
|
||||
titletext = wx.TextCtrl(self.panel,-1,"Not Found!")
|
||||
|
||||
|
||||
else:
|
||||
# self.title.SetValue("Position : "+str(position))
|
||||
|
||||
|
@ -1885,7 +1878,7 @@ class macroed(wx.Dialog):
|
|||
self.callback(self.e.GetValue().split("\n"))
|
||||
def close(self,ev):
|
||||
self.Destroy()
|
||||
if webavail:
|
||||
if self.webInterface:
|
||||
webinterface.KillWebInterfaceThread()
|
||||
def unindent(self,text):
|
||||
self.indent_chars = text[:len(text)-len(text.lstrip())]
|
||||
|
@ -1970,6 +1963,7 @@ class ButtonEdit(wx.Dialog):
|
|||
topsizer.Add( (0,0),1)
|
||||
topsizer.Add(self.CreateStdDialogButtonSizer(wx.OK|wx.CANCEL),0,wx.ALIGN_CENTER)
|
||||
self.SetSizer(topsizer)
|
||||
|
||||
def macrob_enabler(self,e):
|
||||
macro = self.command.GetValue()
|
||||
valid = False
|
||||
|
@ -1994,6 +1988,7 @@ class ButtonEdit(wx.Dialog):
|
|||
else:
|
||||
valid = True
|
||||
self.macrob.Enable(valid)
|
||||
|
||||
def macrob_handler(self,e):
|
||||
macro = self.command.GetValue()
|
||||
macro = self.pronterface.edit_macro(macro)
|
||||
|
@ -2002,6 +1997,7 @@ class ButtonEdit(wx.Dialog):
|
|||
self.name.SetValue(macro)
|
||||
|
||||
class TempGauge(wx.Panel):
|
||||
|
||||
def __init__(self,parent,size=(200,22),title="",maxval=240,gaugeColour=None):
|
||||
wx.Panel.__init__(self,parent,-1,size=size)
|
||||
self.Bind(wx.EVT_PAINT,self.paint)
|
||||
|
@ -2013,17 +2009,21 @@ class TempGauge(wx.Panel):
|
|||
self.value=0
|
||||
self.setpoint=0
|
||||
self.recalc()
|
||||
|
||||
def recalc(self):
|
||||
mmax=max(int(self.setpoint*1.05),self.max)
|
||||
self.scale=float(self.width-2)/float(mmax)
|
||||
self.ypt=max(16,int(self.scale*max(self.setpoint,self.max/6)))
|
||||
|
||||
def SetValue(self,value):
|
||||
self.value=value
|
||||
wx.CallAfter(self.Refresh)
|
||||
|
||||
def SetTarget(self,value):
|
||||
self.setpoint=value
|
||||
self.recalc()
|
||||
wx.CallAfter(self.Refresh)
|
||||
|
||||
def interpolatedColour(self,val,vmin,vmid,vmax,cmin,cmid,cmax):
|
||||
if val < vmin: return cmin
|
||||
if val > vmax: return cmax
|
||||
|
@ -2035,6 +2035,7 @@ class TempGauge(wx.Panel):
|
|||
rgb=lo.Red()+(hi.Red()-lo.Red())*vv,lo.Green()+(hi.Green()-lo.Green())*vv,lo.Blue()+(hi.Blue()-lo.Blue())*vv
|
||||
rgb=map(lambda x:x*0.8,rgb)
|
||||
return wx.Colour(*map(int,rgb))
|
||||
|
||||
def paint(self,ev):
|
||||
x0,y0,x1,y1,xE,yE = 1,1,self.ypt+1,1,self.width+1-2,20
|
||||
dc=wx.PaintDC(self)
|
||||
|
|
|
@ -0,0 +1,152 @@
|
|||
#!/usr/bin/env python
|
||||
|
||||
# This file is part of the Printrun suite.
|
||||
#
|
||||
# Printrun 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 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# Printrun 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 Printrun. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import sys, os, glob
|
||||
import subprocess
|
||||
from stat import *
|
||||
from distutils.core import setup
|
||||
from distutils.command.install import install as _install
|
||||
from distutils.command.install_data import install_data as _install_data
|
||||
|
||||
INSTALLED_FILES = "installed_files"
|
||||
|
||||
class install (_install):
|
||||
|
||||
def run (self):
|
||||
_install.run (self)
|
||||
outputs = self.get_outputs ()
|
||||
length = 0
|
||||
if self.root:
|
||||
length += len (self.root)
|
||||
if self.prefix:
|
||||
length += len (self.prefix)
|
||||
if length:
|
||||
for counter in xrange (len (outputs)):
|
||||
outputs[counter] = outputs[counter][length:]
|
||||
data = "\n".join (outputs)
|
||||
try:
|
||||
file = open (INSTALLED_FILES, "w")
|
||||
except:
|
||||
self.warn ("Could not write installed files list %s" % \
|
||||
INSTALLED_FILES)
|
||||
return
|
||||
file.write (data)
|
||||
file.close ()
|
||||
|
||||
class install_data (_install_data):
|
||||
|
||||
def run (self):
|
||||
def chmod_data_file (file):
|
||||
try:
|
||||
os.chmod (file, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)
|
||||
except:
|
||||
self.warn ("Could not chmod data file %s" % file)
|
||||
_install_data.run (self)
|
||||
map (chmod_data_file, self.get_outputs ())
|
||||
|
||||
class uninstall (_install):
|
||||
|
||||
def run (self):
|
||||
try:
|
||||
file = open (INSTALLED_FILES, "r")
|
||||
except:
|
||||
self.warn ("Could not read installed files list %s" % \
|
||||
INSTALLED_FILES)
|
||||
return
|
||||
files = file.readlines ()
|
||||
file.close ()
|
||||
prepend = ""
|
||||
if self.root:
|
||||
prepend += self.root
|
||||
if self.prefix:
|
||||
prepend += self.prefix
|
||||
if len (prepend):
|
||||
for counter in xrange (len (files)):
|
||||
files[counter] = prepend + files[counter].rstrip ()
|
||||
for file in files:
|
||||
print "Uninstalling %s" % file
|
||||
try:
|
||||
os.unlink (file)
|
||||
except:
|
||||
self.warn ("Could not remove file %s" % file)
|
||||
|
||||
ops = ("install", "build", "sdist", "uninstall", "clean")
|
||||
|
||||
if len (sys.argv) < 2 or sys.argv[1] not in ops:
|
||||
print "Please specify operation : %s" % " | ".join (ops)
|
||||
raise SystemExit
|
||||
|
||||
prefix = None
|
||||
if len (sys.argv) > 2:
|
||||
i = 0
|
||||
for o in sys.argv:
|
||||
if o.startswith ("--prefix"):
|
||||
if o == "--prefix":
|
||||
if len (sys.argv) >= i:
|
||||
prefix = sys.argv[i + 1]
|
||||
sys.argv.remove (prefix)
|
||||
elif o.startswith ("--prefix=") and len (o[9:]):
|
||||
prefix = o[9:]
|
||||
sys.argv.remove (o)
|
||||
i += 1
|
||||
if not prefix and "PREFIX" in os.environ:
|
||||
prefix = os.environ["PREFIX"]
|
||||
if not prefix or not len (prefix):
|
||||
prefix = "/usr/local"
|
||||
|
||||
if sys.argv[1] in ("install", "uninstall") and len (prefix):
|
||||
sys.argv += ["--prefix", prefix]
|
||||
|
||||
target_images_path = "share/pronterface/images/"
|
||||
data_files = [('share/pixmaps/', ['P-face.ico','plater.ico'])]
|
||||
|
||||
for basedir, subdirs, files in os.walk("images"):
|
||||
images = []
|
||||
for filename in files:
|
||||
if filename.find(".svg") or filename.find(".png"):
|
||||
file_path = os.path.join(basedir, filename)
|
||||
images.append(file_path)
|
||||
data_files.append((target_images_path + basedir[len("images/"):], images))
|
||||
|
||||
for basedir, subdirs, files in os.walk("locale"):
|
||||
if not basedir.endswith("LC_MESSAGES"):
|
||||
continue
|
||||
destpath = os.path.join("share", "pronterface", basedir)
|
||||
files = filter(lambda x: x.endswith(".mo"), files)
|
||||
files = map(lambda x: os.path.join(basedir, x), files)
|
||||
data_files.append ((destpath, files))
|
||||
|
||||
extra_data_dirs = ["css"]
|
||||
for extra_data_dir in extra_data_dirs:
|
||||
for basedir, subdirs, files in os.walk(extra_data_dir):
|
||||
files = map(lambda x: os.path.join(basedir, x), files)
|
||||
destpath = os.path.join("share", "pronterface", basedir)
|
||||
data_files.append ((destpath, files))
|
||||
|
||||
setup (
|
||||
name = "Printrun",
|
||||
description = "Host software for 3D printers",
|
||||
author = "Kliment Yanev",
|
||||
url = "http://github.com/kliment/Printrun/",
|
||||
license = "GPLv3",
|
||||
data_files = data_files,
|
||||
packages = ["printrun", "printrun.svg"],
|
||||
scripts = ["pronsole.py", "pronterface.py", "plater.py"],
|
||||
cmdclass = {"uninstall" : uninstall,
|
||||
"install" : install,
|
||||
"install_data" : install_data}
|
||||
)
|
Loading…
Reference in New Issue