Exemple #1
0
    def slice_stl(self, overrides):
        #get the profile from octoprint
        self.progress_pop =  USB_Progress_Popup(roboprinter.lang.pack['Slicer_Wizard']['Progress']['Sub_Title'] + self.file_data['name'], 1)
        self.progress_pop.show()
        self.stl_name = self.file_data['name'].replace(".stl", "")
        self.stl_name = self.stl_name.replace(".STL", "")
        self.stl_name = self.stl_name + ".gcode"
        self.stl_path = roboprinter.printer_instance._file_manager.path_on_disk('local', self.file_data['path'])
        self.overrides = overrides

        Clock.schedule_once(self.start_slice, 0.1)
Exemple #2
0
    def slice_stl(self, name, path, overrides):
        #get the profile from octoprint
        self.progress_pop = USB_Progress_Popup(
            roboprinter.lang.pack['Slicer_Wizard']['Progress']['Sub_Title'] +
            name, 1)
        self.progress_pop.show()
        self.stl_name = name.replace(".stl", "")
        self.stl_name = self.stl_name.replace(".STL", "")
        self.stl_name = self.stl_name + ".gcode"
        self.stl_path = path
        self.overrides = overrides

        Clock.schedule_once(self.start_slice, 0.1)
Exemple #3
0
class Slicer_Wizard(FloatLayout):
    def __init__(self, robosm, back_destination):
        super(Slicer_Wizard, self).__init__()

        #make default meta data
        self.meta = {
            'layer height': '--',
            'layers': '--',
            'infill': '--',
            'time': {
                'hours': str(0),
                'minutes': str(0),
                'seconds': str(0)
            }
        }
        #make sure the tmp directory exists
        self.search_for_temp_dir()

        self.sm = robosm
        self.oprint = roboprinter.printer_instance

        #show the confirmation screen

        self.show_confirmation_screen()

    def show_confirmation_screen(self):
        next_action = self.open_file_select_screen
        screen_name = "slicing wizard"
        title = roboprinter.lang.pack['Slicer_Wizard']['Confirmation']['Title']
        back_destination = self.sm.current
        layout = STL_Confirmation_Screen(next_action)
        self.sm._generate_backbutton_screen(name=screen_name,
                                            title=title,
                                            back_destination=back_destination,
                                            content=layout)

    def open_file_select_screen(self):
        layout = File_Explorer('model',
                               self.create_button,
                               enable_editing=False)
        #continue to the stl select screen
        back_destination = self.sm.current
        title = roboprinter.lang.pack['Slicer_Wizard']['Select_File']['Title']
        name = "choose_file"

        self.sm._generate_backbutton_screen(name=name,
                                            title=title,
                                            back_destination=back_destination,
                                            content=layout)

    #a helper function so we can use the file explorer
    def create_button(self, filename, date, path, **kwargs):
        return stl_Button(filename, path, date, self.choose_overrides)

    def search_for_temp_dir(self):
        if not os.path.exists(TEMP_DIR):
            os.makedirs(TEMP_DIR)
            Logger.info("Made temp directory for slicing")

    def choose_overrides(self, name, path):
        screen_name = 'slicer_overrides'
        title = roboprinter.lang.pack['Slicer_Wizard']['Overrides']['Title']
        back_destination = self.sm.current
        real_path = roboprinter.printer_instance._file_manager.path_on_disk(
            'local', path)
        Logger.info(real_path)
        layout = Override_Page(name, real_path, self.slice_stl)

    def slice_stl(self, name, path, overrides):
        #get the profile from octoprint
        self.progress_pop = USB_Progress_Popup(
            roboprinter.lang.pack['Slicer_Wizard']['Progress']['Sub_Title'] +
            name, 1)
        self.progress_pop.show()
        self.stl_name = name.replace(".stl", "")
        self.stl_name = self.stl_name.replace(".STL", "")
        self.stl_name = self.stl_name + ".gcode"
        self.stl_path = path
        self.overrides = overrides

        Clock.schedule_once(self.start_slice, 0.1)

    def start_slice(self, dt):

        profiles = roboprinter.printer_instance._slicing_manager.all_profiles(
            'cura', require_configured=False)
        if 'robo' in profiles:
            #start slice
            self.temp_path = TEMP_DIR + "/" + self.stl_name
            Logger.info("Starting Slice")
            Logger.info(self.overrides)
            roboprinter.printer_instance._slicing_manager.slice(
                'cura',
                self.stl_path,
                self.temp_path,
                'robo',
                self.sliced,
                overrides=self.overrides,
                on_progress=self.slice_progress)
        else:
            #put our profile in the profile list
            profile_path = os.path.dirname(os.path.realpath(__file__))
            profile_path += '/slicer_profile/robo.profile'

            if os.path.isfile(profile_path):
                #copy a backup of the profile to the default profile directory
                shutil.copyfile(profile_path, CURA_DIR + '/robo.profile')

                #if the backup exists and we have tried restoring it 5 times give up and error out
                if dt < 5:
                    Logger.info('Restarting the slice, Rec Depth = ' +
                                str(dt + 1))
                    self.start_slice(dt + 1)
                else:
                    ep = Error_Popup(roboprinter.lang.pack['Slicer_Wizard']
                                     ['Error']['Profile']['Sub_Title'],
                                     roboprinter.lang.pack['Slicer_Wizard']
                                     ['Error']['Profile']['Body'],
                                     callback=partial(
                                         roboprinter.robosm.go_back_to_main,
                                         tab='printer_status_tab'))
                    ep.show()
            #if the backup does not exist then error out
            else:
                Logger.info('Slicer Error: Path Does not exist')
                ep = Error_Popup(roboprinter.lang.pack['Slicer_Wizard']
                                 ['Error']['Profile']['Sub_Title'],
                                 roboprinter.lang.pack['Slicer_Wizard']
                                 ['Error']['Profile']['Body'],
                                 callback=partial(
                                     roboprinter.robosm.go_back_to_main,
                                     tab='printer_status_tab'))
                ep.show()

    def sliced(self, **kwargs):
        Logger.info(kwargs)
        if '_error' in kwargs:
            #doing this will get rid of graphical errors. Kivy does not like being managed from an outside thread.
            Logger.info(str(kwargs['_error']))
            Clock.schedule_once(self.error_pop, 0.01)
        elif '_analysis' in kwargs:
            #initialize meta data
            ept = 0
            lh = str(self.overrides['layer_height'])
            infill = str(self.overrides['fill_density'])
            if 'estimatedPrintTime' in kwargs['_analysis']:
                ept = kwargs['_analysis']['estimatedPrintTime']
            #save meta data
            self.meta = {'layer height': lh, 'infill': infill, 'time': ept}

            Logger.info("finished Slice")
            self.progress_pop.hide()
            #after slicing ask the user where they want the file to be saved at
            Clock.schedule_once(self.save_file, 0.01)

        else:
            Logger.info("finished Slice")
            self.progress_pop.hide()
            #after slicing ask the user where they want the file to be saved at
            Clock.schedule_once(self.save_file, 0.01)

    def error_pop(self, dt, *args, **kwargs):
        self.progress_pop.hide()

        os.remove(self.temp_path)
        ep = Error_Popup(
            roboprinter.lang.pack['Slicer_Wizard']['Error']['Slice']
            ['Sub_Title'],
            roboprinter.lang.pack['Slicer_Wizard']['Error']['Slice']['Body'],
            callback=partial(roboprinter.robosm.go_back_to_main,
                             tab='printer_status_tab'))
        ep.show()

    # This takes a number in seconds and returns a dictionary of the hours/minutes/seconds
    def parse_time(self, time):
        m, s = divmod(time, 60)
        h, m = divmod(m, 60)

        time_dict = {'hours': str(h), 'minutes': str(m), 'seconds': str(s)}

        return time_dict

    # this function exists because calling the Save_File class directly from the sliced function resulted in Graphical issues
    # Setting a clock to call this function fixed the graphical issues. I believe it is because the sliced function gets called
    # by the slicing manager thread, and graphical issues do present themselves when calling kivy objects outside the thread
    # they are created in.
    def save_file(self, dt):
        Logger.info('Saving data ' + self.temp_path +
                    ' along with the meta data: ' + str(self.meta))
        Save_File(self.temp_path, meta_data=self.meta)

    def slice_progress(self, *args, **kwargs):
        if '_progress' in kwargs:
            #Logger.info(str(kwargs['_progress']))
            self.current_progress = kwargs['_progress']
            #Just trying to avoid graphical issues
            Clock.schedule_once(self.get_progress, 0)

    def get_progress(self, dt, *args, **kwargs):
        self.progress_pop.update_progress(self.current_progress)
Exemple #4
0
 def __init__(self, **kwargs):
     super(PrintUSB, self).__init__(**kwargs)
     self.progress_pop = USB_Progress_Popup("Saving File", 1)
     pass
Exemple #5
0
class PrintUSB(PrintFile):
    """
        This class encapsulates the dynamic properties that get rendered on the PrintUSB and the methods that allow the user to start a print from usb or save the file to local.
    """
    def __init__(self, **kwargs):
        super(PrintUSB, self).__init__(**kwargs)
        self.progress_pop = USB_Progress_Popup("Saving File", 1)
        pass

    def save_file_to_local(self, *args):
        self.progress_pop.show()

        Clock.schedule_once(self.attempt_to_save, 0.01)

    def attempt_to_save(self, dt):
        try:
            copy_path = FILES_DIR + '/' + self.file_name
            real_path = roboprinter.printer_instance._file_manager.path_on_disk(
                'local', self.file_path)

            #shutil.copy2(real_path, copy_path)
            Logger.info("Started the Copy src: " + real_path + " cp to dst: " +
                        copy_path)
            copied = self.copy_file(real_path,
                                    copy_path,
                                    progress_callback=self.progress_update)
            if not copied:
                self.progress_pop.hide()
                ep = Error_Popup(
                    roboprinter.lang.pack['Files']['File_Error']['Title'],
                    roboprinter.lang.pack['Files']['File_Error']['Body'],
                    callback=partial(roboprinter.robosm.go_back_to_main,
                                     tab='printer_status_tab'))
                ep.show()
                Logger.info("attempt to save Error")

        except Exception as e:
            #raise error
            self.progress_pop.hide()
            ep = Error_Popup(
                roboprinter.lang.pack['Files']['File_Error']['Title'],
                roboprinter.lang.pack['Files']['File_Error']['Body'],
                callback=partial(roboprinter.robosm.go_back_to_main,
                                 tab='printer_status_tab'))
            ep.show()
            Logger.info("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! " + str(e))
            traceback.print_exc()

    def copy_file(self,
                  fsrc,
                  fdst,
                  progress_callback=None,
                  complete_callback=None,
                  length=16 * 1024,
                  **kwargs):

        self.copied = 0
        self.file_size = 0
        self.length = length
        self.p_callback = progress_callback
        self.c_callback = complete_callback
        if not os.path.isfile(fsrc):
            Logger.info("Will not copy")
            return False

        else:
            self.file_size = float(os.path.getsize(fsrc))
        #make the new file
        self.src_obj = open(fsrc, 'rb')
        self.dst_obj = open(fdst, 'wb')
        #Do the copy as fast as possible without blocking the UI thread
        Clock.schedule_interval(self.copy_object, 0)
        return True

    #doing it this way with a clock object does not block the UI
    def copy_object(self, dt):
        #grab part of the file
        buf = self.src_obj.read(self.length)
        #if there isn't anything to read then close the files and return
        if not buf:
            self.src_obj.close()
            self.dst_obj.close()
            if self.c_callback != None:
                self.c_callback()
            return False
        #Write the buffer to the new file
        self.dst_obj.write(buf)
        #update how much of the file has been copied
        self.copied += len(buf)

        #report progress
        if self.p_callback != None:
            progress = float(self.copied / self.file_size)
            self.p_callback(progress)

    def progress_update(self, progress):
        self.progress_pop.update_progress(progress)
        #Logger.info(str(progress))

        if progress == 1.0:
            self.progress_pop.hide()
            ep = Error_Popup(
                roboprinter.lang.pack['Files']['File_Saved']['Title'],
                roboprinter.lang.pack['Files']['File_Saved']['Body'],
                callback=partial(roboprinter.robosm.go_back_to_main,
                                 tab='printer_status_tab'))
            ep.show()
            if 'file_callback' in session_saver.saved:
                session_saver.saved['file_callback']()