diff --git a/FlatCAM.py b/FlatCAM.py index 92b1ad86..440181f0 100644 --- a/FlatCAM.py +++ b/FlatCAM.py @@ -6,6 +6,7 @@ from FlatCAMApp import App from multiprocessing import freeze_support import VisPyPatches + if sys.platform == "win32": # cx_freeze 'module win32' workaround import OpenGL.platform.win32 diff --git a/FlatCAMApp.py b/FlatCAMApp.py index fed5f39c..37e2c233 100644 --- a/FlatCAMApp.py +++ b/FlatCAMApp.py @@ -104,6 +104,7 @@ class App(QtCore.QObject): manual_url = "http://flatcam.org/manual/index.html" video_url = "https://www.youtube.com/playlist?list=PLVvP2SYRpx-AQgNlfoxw93tXUXon7G94_" + should_we_quit = True ################## ## Signals ## @@ -291,25 +292,25 @@ class App(QtCore.QObject): # when adding entries here read the comments in the method found bellow named: # def new_object(self, kind, name, initialize, active=True, fit=True, plot=True) self.defaults_form_fields = { - "units": self.general_defaults_form.general_group.units_radio, - "global_shell_at_startup": self.general_defaults_form.general_group.shell_startup_cb, - "global_version_check": self.general_defaults_form.general_group.version_check_cb, - "global_send_stats": self.general_defaults_form.general_group.send_stats_cb, - "global_gridx": self.general_defaults_form.general_group.gridx_entry, - "global_gridy": self.general_defaults_form.general_group.gridy_entry, - "global_plot_fill": self.general_defaults_form.general_group.pf_color_entry, - "global_plot_line": self.general_defaults_form.general_group.pl_color_entry, - "global_sel_fill": self.general_defaults_form.general_group.sf_color_entry, - "global_sel_line": self.general_defaults_form.general_group.sl_color_entry, - "global_alt_sel_fill": self.general_defaults_form.general_group.alt_sf_color_entry, - "global_alt_sel_line": self.general_defaults_form.general_group.alt_sl_color_entry, - "global_draw_color": self.general_defaults_form.general_group.draw_color_entry, - "global_sel_draw_color": self.general_defaults_form.general_group.sel_draw_color_entry, - "global_pan_button": self.general_defaults_form.general_group.pan_button_radio, - "global_mselect_key": self.general_defaults_form.general_group.mselect_radio, - # "global_pan_with_space_key": self.general_defaults_form.general_group.pan_with_space_cb, - "global_workspace": self.general_defaults_form.general_group.workspace_cb, - "global_workspaceT": self.general_defaults_form.general_group.wk_cb, + "units": self.general_defaults_form.general_app_group.units_radio, + "global_shell_at_startup": self.general_defaults_form.general_app_group.shell_startup_cb, + "global_version_check": self.general_defaults_form.general_app_group.version_check_cb, + "global_send_stats": self.general_defaults_form.general_app_group.send_stats_cb, + "global_gridx": self.general_defaults_form.general_gui_group.gridx_entry, + "global_gridy": self.general_defaults_form.general_gui_group.gridy_entry, + "global_plot_fill": self.general_defaults_form.general_gui_group.pf_color_entry, + "global_plot_line": self.general_defaults_form.general_gui_group.pl_color_entry, + "global_sel_fill": self.general_defaults_form.general_gui_group.sf_color_entry, + "global_sel_line": self.general_defaults_form.general_gui_group.sl_color_entry, + "global_alt_sel_fill": self.general_defaults_form.general_gui_group.alt_sf_color_entry, + "global_alt_sel_line": self.general_defaults_form.general_gui_group.alt_sl_color_entry, + "global_draw_color": self.general_defaults_form.general_gui_group.draw_color_entry, + "global_sel_draw_color": self.general_defaults_form.general_gui_group.sel_draw_color_entry, + "global_pan_button": self.general_defaults_form.general_app_group.pan_button_radio, + "global_mselect_key": self.general_defaults_form.general_app_group.mselect_radio, + # "global_pan_with_space_key": self.general_defaults_form.general_gui_group.pan_with_space_cb, + "global_workspace": self.general_defaults_form.general_gui_group.workspace_cb, + "global_workspaceT": self.general_defaults_form.general_gui_group.wk_cb, "gerber_plot": self.gerber_defaults_form.gerber_group.plot_cb, "gerber_solid": self.gerber_defaults_form.gerber_group.solid_cb, @@ -582,9 +583,9 @@ class App(QtCore.QObject): self.cncjob_options_form = CNCJobPreferencesUI() self.options_form_fields = { - "units": self.general_options_form.general_group.units_radio, - "global_gridx": self.general_options_form.general_group.gridx_entry, - "global_gridy": self.general_options_form.general_group.gridy_entry, + "units": self.general_options_form.general_app_group.units_radio, + "global_gridx": self.general_options_form.general_gui_group.gridx_entry, + "global_gridy": self.general_options_form.general_gui_group.gridy_entry, "gerber_plot": self.gerber_options_form.gerber_group.plot_cb, "gerber_solid": self.gerber_options_form.gerber_group.solid_cb, "gerber_multicolored": self.gerber_options_form.gerber_group.multicolored_cb, @@ -758,51 +759,51 @@ class App(QtCore.QObject): ### Initialize the color box's color in Preferences -> Global -> Color # Init Plot Colors - self.general_defaults_form.general_group.pf_color_entry.set_value(self.defaults['global_plot_fill']) - self.general_defaults_form.general_group.pf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.pf_color_entry.set_value(self.defaults['global_plot_fill']) + self.general_defaults_form.general_gui_group.pf_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_plot_fill'])[:7]) - self.general_defaults_form.general_group.pf_color_alpha_spinner.set_value( + self.general_defaults_form.general_gui_group.pf_color_alpha_spinner.set_value( int(self.defaults['global_plot_fill'][7:9], 16)) - self.general_defaults_form.general_group.pf_color_alpha_slider.setValue( + self.general_defaults_form.general_gui_group.pf_color_alpha_slider.setValue( int(self.defaults['global_plot_fill'][7:9], 16)) - self.general_defaults_form.general_group.pl_color_entry.set_value(self.defaults['global_plot_line']) - self.general_defaults_form.general_group.pl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.pl_color_entry.set_value(self.defaults['global_plot_line']) + self.general_defaults_form.general_gui_group.pl_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_plot_line'])[:7]) # Init Left-Right Selection colors - self.general_defaults_form.general_group.sf_color_entry.set_value(self.defaults['global_sel_fill']) - self.general_defaults_form.general_group.sf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sf_color_entry.set_value(self.defaults['global_sel_fill']) + self.general_defaults_form.general_gui_group.sf_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_sel_fill'])[:7]) - self.general_defaults_form.general_group.sf_color_alpha_spinner.set_value( + self.general_defaults_form.general_gui_group.sf_color_alpha_spinner.set_value( int(self.defaults['global_sel_fill'][7:9], 16)) - self.general_defaults_form.general_group.sf_color_alpha_slider.setValue( + self.general_defaults_form.general_gui_group.sf_color_alpha_slider.setValue( int(self.defaults['global_sel_fill'][7:9], 16)) - self.general_defaults_form.general_group.sl_color_entry.set_value(self.defaults['global_sel_line']) - self.general_defaults_form.general_group.sl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sl_color_entry.set_value(self.defaults['global_sel_line']) + self.general_defaults_form.general_gui_group.sl_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_sel_line'])[:7]) # Init Right-Left Selection colors - self.general_defaults_form.general_group.alt_sf_color_entry.set_value(self.defaults['global_alt_sel_fill']) - self.general_defaults_form.general_group.alt_sf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.alt_sf_color_entry.set_value(self.defaults['global_alt_sel_fill']) + self.general_defaults_form.general_gui_group.alt_sf_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_alt_sel_fill'])[:7]) - self.general_defaults_form.general_group.alt_sf_color_alpha_spinner.set_value( + self.general_defaults_form.general_gui_group.alt_sf_color_alpha_spinner.set_value( int(self.defaults['global_sel_fill'][7:9], 16)) - self.general_defaults_form.general_group.alt_sf_color_alpha_slider.setValue( + self.general_defaults_form.general_gui_group.alt_sf_color_alpha_slider.setValue( int(self.defaults['global_sel_fill'][7:9], 16)) - self.general_defaults_form.general_group.alt_sl_color_entry.set_value(self.defaults['global_alt_sel_line']) - self.general_defaults_form.general_group.alt_sl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.alt_sl_color_entry.set_value(self.defaults['global_alt_sel_line']) + self.general_defaults_form.general_gui_group.alt_sl_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_alt_sel_line'])[:7]) # Init Draw color and Selection Draw Color - self.general_defaults_form.general_group.draw_color_entry.set_value(self.defaults['global_draw_color']) - self.general_defaults_form.general_group.draw_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.draw_color_entry.set_value(self.defaults['global_draw_color']) + self.general_defaults_form.general_gui_group.draw_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_draw_color'])[:7]) - self.general_defaults_form.general_group.sel_draw_color_entry.set_value(self.defaults['global_sel_draw_color']) - self.general_defaults_form.general_group.sel_draw_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sel_draw_color_entry.set_value(self.defaults['global_sel_draw_color']) + self.general_defaults_form.general_gui_group.sel_draw_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_sel_draw_color'])[:7]) #### End of Data #### @@ -917,6 +918,7 @@ class App(QtCore.QObject): self.ui.menueditorigin.triggered.connect(self.on_set_origin) self.ui.menueditjump.triggered.connect(self.on_jump_to) + self.ui.menuedittoggleunits.triggered.connect(self.on_toggle_units_click) self.ui.menueditselectall.triggered.connect(self.on_selectall) self.ui.menueditpreferences.triggered.connect(self.on_preferences) @@ -942,6 +944,7 @@ class App(QtCore.QObject): self.ui.menuview_zoom_fit.triggered.connect(self.on_zoom_fit) self.ui.menuview_zoom_in.triggered.connect(lambda: self.plotcanvas.zoom(1 / 1.5)) self.ui.menuview_zoom_out.triggered.connect(lambda: self.plotcanvas.zoom(1.5)) + self.ui.menuview_toggle_grid.triggered.connect(self.on_toggle_grid) self.ui.menuview_toggle_axis.triggered.connect(self.on_toggle_axis) self.ui.menuview_toggle_workspace.triggered.connect(self.on_workspace_menu) @@ -995,6 +998,7 @@ class App(QtCore.QObject): self.ui.draw_line.triggered.connect(self.geo_editor.draw_tool_path) self.ui.draw_rect.triggered.connect(self.geo_editor.draw_tool_rectangle) self.ui.draw_cut.triggered.connect(self.geo_editor.cutpath) + self.ui.draw_move.triggered.connect(self.geo_editor.on_move) self.ui.drill.triggered.connect(self.exc_editor.exc_add_drill) self.ui.drill_array.triggered.connect(self.exc_editor.exc_add_drill_array) self.ui.drill_copy.triggered.connect(self.exc_editor.exc_copy_drills) @@ -1019,39 +1023,48 @@ class App(QtCore.QObject): self.ui.pref_export_button.clicked.connect(self.on_export_preferences) self.ui.pref_open_button.clicked.connect(self.on_preferences_open_folder) - self.general_options_form.general_group.units_radio.group_toggle_fn = self.on_toggle_units + ############################### + ### GUI PREFERENCES SIGNALS ### + ############################### + self.general_options_form.general_app_group.units_radio.group_toggle_fn = self.on_toggle_units + self.general_defaults_form.general_app_group.language_apply_btn.clicked.connect(self.on_language_apply) + + ############################### + ### GUI PREFERENCES SIGNALS ### + ############################### + # Setting plot colors signals - self.general_defaults_form.general_group.pf_color_entry.editingFinished.connect(self.on_pf_color_entry) - self.general_defaults_form.general_group.pf_color_button.clicked.connect(self.on_pf_color_button) - self.general_defaults_form.general_group.pf_color_alpha_spinner.valueChanged.connect(self.on_pf_color_spinner) - self.general_defaults_form.general_group.pf_color_alpha_slider.valueChanged.connect(self.on_pf_color_slider) - self.general_defaults_form.general_group.pl_color_entry.editingFinished.connect(self.on_pl_color_entry) - self.general_defaults_form.general_group.pl_color_button.clicked.connect(self.on_pl_color_button) + self.general_defaults_form.general_gui_group.pf_color_entry.editingFinished.connect(self.on_pf_color_entry) + self.general_defaults_form.general_gui_group.pf_color_button.clicked.connect(self.on_pf_color_button) + self.general_defaults_form.general_gui_group.pf_color_alpha_spinner.valueChanged.connect(self.on_pf_color_spinner) + self.general_defaults_form.general_gui_group.pf_color_alpha_slider.valueChanged.connect(self.on_pf_color_slider) + self.general_defaults_form.general_gui_group.pl_color_entry.editingFinished.connect(self.on_pl_color_entry) + self.general_defaults_form.general_gui_group.pl_color_button.clicked.connect(self.on_pl_color_button) # Setting selection (left - right) colors signals - self.general_defaults_form.general_group.sf_color_entry.editingFinished.connect(self.on_sf_color_entry) - self.general_defaults_form.general_group.sf_color_button.clicked.connect(self.on_sf_color_button) - self.general_defaults_form.general_group.sf_color_alpha_spinner.valueChanged.connect(self.on_sf_color_spinner) - self.general_defaults_form.general_group.sf_color_alpha_slider.valueChanged.connect(self.on_sf_color_slider) - self.general_defaults_form.general_group.sl_color_entry.editingFinished.connect(self.on_sl_color_entry) - self.general_defaults_form.general_group.sl_color_button.clicked.connect(self.on_sl_color_button) + self.general_defaults_form.general_gui_group.sf_color_entry.editingFinished.connect(self.on_sf_color_entry) + self.general_defaults_form.general_gui_group.sf_color_button.clicked.connect(self.on_sf_color_button) + self.general_defaults_form.general_gui_group.sf_color_alpha_spinner.valueChanged.connect(self.on_sf_color_spinner) + self.general_defaults_form.general_gui_group.sf_color_alpha_slider.valueChanged.connect(self.on_sf_color_slider) + self.general_defaults_form.general_gui_group.sl_color_entry.editingFinished.connect(self.on_sl_color_entry) + self.general_defaults_form.general_gui_group.sl_color_button.clicked.connect(self.on_sl_color_button) # Setting selection (right - left) colors signals - self.general_defaults_form.general_group.alt_sf_color_entry.editingFinished.connect(self.on_alt_sf_color_entry) - self.general_defaults_form.general_group.alt_sf_color_button.clicked.connect(self.on_alt_sf_color_button) - self.general_defaults_form.general_group.alt_sf_color_alpha_spinner.valueChanged.connect( + self.general_defaults_form.general_gui_group.alt_sf_color_entry.editingFinished.connect(self.on_alt_sf_color_entry) + self.general_defaults_form.general_gui_group.alt_sf_color_button.clicked.connect(self.on_alt_sf_color_button) + self.general_defaults_form.general_gui_group.alt_sf_color_alpha_spinner.valueChanged.connect( self.on_alt_sf_color_spinner) - self.general_defaults_form.general_group.alt_sf_color_alpha_slider.valueChanged.connect( + self.general_defaults_form.general_gui_group.alt_sf_color_alpha_slider.valueChanged.connect( self.on_alt_sf_color_slider) - self.general_defaults_form.general_group.alt_sl_color_entry.editingFinished.connect(self.on_alt_sl_color_entry) - self.general_defaults_form.general_group.alt_sl_color_button.clicked.connect(self.on_alt_sl_color_button) + self.general_defaults_form.general_gui_group.alt_sl_color_entry.editingFinished.connect(self.on_alt_sl_color_entry) + self.general_defaults_form.general_gui_group.alt_sl_color_button.clicked.connect(self.on_alt_sl_color_button) # Setting Editor Draw colors signals - self.general_defaults_form.general_group.draw_color_entry.editingFinished.connect(self.on_draw_color_entry) - self.general_defaults_form.general_group.draw_color_button.clicked.connect(self.on_draw_color_button) + self.general_defaults_form.general_gui_group.draw_color_entry.editingFinished.connect(self.on_draw_color_entry) + self.general_defaults_form.general_gui_group.draw_color_button.clicked.connect(self.on_draw_color_button) - self.general_defaults_form.general_group.sel_draw_color_entry.editingFinished.connect(self.on_sel_draw_color_entry) - self.general_defaults_form.general_group.sel_draw_color_button.clicked.connect(self.on_sel_draw_color_button) + self.general_defaults_form.general_gui_group.sel_draw_color_entry.editingFinished.connect(self.on_sel_draw_color_entry) + self.general_defaults_form.general_gui_group.sel_draw_color_button.clicked.connect(self.on_sel_draw_color_button) - self.general_defaults_form.general_group.wk_cb.currentIndexChanged.connect(self.on_workspace_modified) - self.general_defaults_form.general_group.workspace_cb.stateChanged.connect(self.on_workspace) + self.general_defaults_form.general_gui_group.wk_cb.currentIndexChanged.connect(self.on_workspace_modified) + self.general_defaults_form.general_gui_group.workspace_cb.stateChanged.connect(self.on_workspace) # Modify G-CODE Plot Area TAB @@ -1067,7 +1080,7 @@ class App(QtCore.QObject): self.collection.view.activated.connect(self.on_row_activated) # Monitor the checkbox from the Application Defaults Tab and show the TCL shell or not depending on it's value - self.general_defaults_form.general_group.shell_startup_cb.clicked.connect(self.on_toggle_shell) + self.general_defaults_form.general_app_group.shell_startup_cb.clicked.connect(self.on_toggle_shell) # Load the defaults values into the Excellon Format and Excellon Zeros fields self.excellon_defaults_form.excellon_group.excellon_defaults_button.clicked.connect( @@ -1173,7 +1186,7 @@ class App(QtCore.QObject): # Separate thread (Not worker) # Check for updates on startup but only if the user consent and the app is not in Beta version if (self.beta is False or self.beta is None) and \ - self.general_defaults_form.general_group.version_check_cb.get_value() is True: + self.general_defaults_form.general_gui_group.version_check_cb.get_value() is True: App.log.info("Checking for updates in backgroud (this is version %s)." % str(self.version)) self.thr2 = QtCore.QThread() @@ -2214,13 +2227,16 @@ class App(QtCore.QObject): "Do you want to Save the project?") msgbox.setWindowTitle("Save changes") msgbox.setWindowIcon(QtGui.QIcon('share/save_as.png')) - msgbox.setStandardButtons(QtWidgets.QMessageBox.Cancel | QtWidgets.QMessageBox.Ok) - msgbox.setDefaultButton(QtWidgets.QMessageBox.Ok) + msgbox.setStandardButtons(QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No | + QtWidgets.QMessageBox.Cancel) + msgbox.setDefaultButton(QtWidgets.QMessageBox.Yes) response = msgbox.exec_() - if response == QtWidgets.QMessageBox.Ok: + if response == QtWidgets.QMessageBox.Yes: self.on_file_saveprojectas(thread=False) + elif response == QtWidgets.QMessageBox.Cancel: + return self.save_defaults() else: self.save_defaults() @@ -2350,14 +2366,17 @@ class App(QtCore.QObject): "Do you want to Save the project?") msgbox.setWindowTitle("Save changes") msgbox.setWindowIcon(QtGui.QIcon('share/save_as.png')) - msgbox.setStandardButtons(QtWidgets.QMessageBox.Cancel | QtWidgets.QMessageBox.Ok) - msgbox.setDefaultButton(QtWidgets.QMessageBox.Ok) + msgbox.setStandardButtons(QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No | + QtWidgets.QMessageBox.Cancel) + msgbox.setDefaultButton(QtWidgets.QMessageBox.Yes) response = msgbox.exec_() - if response == QtWidgets.QMessageBox.Ok: + if response == QtWidgets.QMessageBox.Yes: self.on_file_saveprojectas(thread=False) - + elif response == QtWidgets.QMessageBox.Cancel: + self.should_we_quit = False + return self.save_defaults() log.debug("Application defaults saved ... Exit event.") @@ -2508,7 +2527,7 @@ class App(QtCore.QObject): return # If option is the same, then ignore - if self.general_options_form.general_group.units_radio.get_value().upper() == self.options["units"].upper(): + if self.general_options_form.general_app_group.units_radio.get_value().upper() == self.options["units"].upper(): self.log.debug("on_toggle_units(): Same as options, so ignoring.") return @@ -2542,7 +2561,7 @@ class App(QtCore.QObject): # The scaling factor depending on choice of units. factor = 1/25.4 - if self.general_options_form.general_group.units_radio.get_value().upper() == 'MM': + if self.general_options_form.general_app_group.units_radio.get_value().upper() == 'MM': factor = 25.4 @@ -2570,7 +2589,7 @@ class App(QtCore.QObject): self.ui.grid_gap_y_entry.set_value(float(self.ui.grid_gap_y_entry.get_value()) * factor) for obj in self.collection.get_list(): - units = self.general_options_form.general_group.units_radio.get_value().upper() + units = self.general_options_form.general_app_group.units_radio.get_value().upper() obj.convert_units(units) # make that the properties stored in the object are also updated @@ -2587,10 +2606,10 @@ class App(QtCore.QObject): else: # Undo toggling self.toggle_units_ignore = True - if self.general_options_form.general_group.units_radio.get_value().upper() == 'MM': - self.general_options_form.general_group.units_radio.set_value('IN') + if self.general_options_form.general_app_group.units_radio.get_value().upper() == 'MM': + self.general_options_form.general_app_group.units_radio.set_value('IN') else: - self.general_options_form.general_group.units_radio.set_value('MM') + self.general_options_form.general_app_group.units_radio.set_value('MM') self.toggle_units_ignore = False self.options_read_form() @@ -2598,6 +2617,18 @@ class App(QtCore.QObject): #self.ui.units_label.setText("[" + self.options["units"] + "]") self.set_screen_units(self.options["units"]) + def on_toggle_units_click(self): + if self.options["units"] == 'MM': + self.general_options_form.general_app_group.units_radio.set_value("IN") + else: + self.general_options_form.general_app_group.units_radio.set_value("MM") + self.on_toggle_units() + + def on_language_apply(self): + # TODO: apply the language + # app restart section + pass + def on_toggle_axis(self): if self.toggle_axis is False: self.plotcanvas.v_line.set_data(color=(0.70, 0.3, 0.3, 1.0)) @@ -2611,6 +2642,9 @@ class App(QtCore.QObject): self.plotcanvas.redraw() self.toggle_axis = False + def on_toggle_grid(self): + self.ui.grid_snap_btn.trigger() + def on_options_combo_change(self, sel): """ Called when the combo box to choose between application defaults and @@ -2702,9 +2736,9 @@ class App(QtCore.QObject): # Setting plot colors handlers def on_pf_color_entry(self): - self.defaults['global_plot_fill'] = self.general_defaults_form.general_group.pf_color_entry.get_value()[:7] + \ + self.defaults['global_plot_fill'] = self.general_defaults_form.general_gui_group.pf_color_entry.get_value()[:7] + \ self.defaults['global_plot_fill'][7:9] - self.general_defaults_form.general_group.pf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.pf_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_plot_fill'])[:7]) def on_pf_color_button(self): @@ -2716,29 +2750,29 @@ class App(QtCore.QObject): if plot_fill_color.isValid() is False: return - self.general_defaults_form.general_group.pf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.pf_color_button.setStyleSheet( "background-color:%s" % str(plot_fill_color.name())) new_val = str(plot_fill_color.name()) + str(self.defaults['global_plot_fill'][7:9]) - self.general_defaults_form.general_group.pf_color_entry.set_value(new_val) + self.general_defaults_form.general_gui_group.pf_color_entry.set_value(new_val) self.defaults['global_plot_fill'] = new_val def on_pf_color_spinner(self): - spinner_value = self.general_defaults_form.general_group.pf_color_alpha_spinner.value() - self.general_defaults_form.general_group.pf_color_alpha_slider.setValue(spinner_value) + spinner_value = self.general_defaults_form.general_gui_group.pf_color_alpha_spinner.value() + self.general_defaults_form.general_gui_group.pf_color_alpha_slider.setValue(spinner_value) self.defaults['global_plot_fill'] = self.defaults['global_plot_fill'][:7] + \ (hex(spinner_value)[2:] if int(hex(spinner_value)[2:], 16) > 0 else '00') self.defaults['global_plot_line'] = self.defaults['global_plot_line'][:7] + \ (hex(spinner_value)[2:] if int(hex(spinner_value)[2:], 16) > 0 else '00') def on_pf_color_slider(self): - slider_value = self.general_defaults_form.general_group.pf_color_alpha_slider.value() - self.general_defaults_form.general_group.pf_color_alpha_spinner.setValue(slider_value) + slider_value = self.general_defaults_form.general_gui_group.pf_color_alpha_slider.value() + self.general_defaults_form.general_gui_group.pf_color_alpha_spinner.setValue(slider_value) def on_pl_color_entry(self): - self.defaults['global_plot_line'] = self.general_defaults_form.general_group.pl_color_entry.get_value()[:7] + \ + self.defaults['global_plot_line'] = self.general_defaults_form.general_gui_group.pl_color_entry.get_value()[:7] + \ self.defaults['global_plot_line'][7:9] - self.general_defaults_form.general_group.pl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.pl_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_plot_line'])[:7]) def on_pl_color_button(self): @@ -2751,18 +2785,18 @@ class App(QtCore.QObject): if plot_line_color.isValid() is False: return - self.general_defaults_form.general_group.pl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.pl_color_button.setStyleSheet( "background-color:%s" % str(plot_line_color.name())) new_val_line = str(plot_line_color.name()) + str(self.defaults['global_plot_line'][7:9]) - self.general_defaults_form.general_group.pl_color_entry.set_value(new_val_line) + self.general_defaults_form.general_gui_group.pl_color_entry.set_value(new_val_line) self.defaults['global_plot_line'] = new_val_line # Setting selection colors (left - right) handlers def on_sf_color_entry(self): - self.defaults['global_sel_fill'] = self.general_defaults_form.general_group.sf_color_entry.get_value()[:7] + \ + self.defaults['global_sel_fill'] = self.general_defaults_form.general_gui_group.sf_color_entry.get_value()[:7] + \ self.defaults['global_sel_fill'][7:9] - self.general_defaults_form.general_group.sf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sf_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_sel_fill'])[:7]) def on_sf_color_button(self): @@ -2774,29 +2808,29 @@ class App(QtCore.QObject): if plot_fill_color.isValid() is False: return - self.general_defaults_form.general_group.sf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sf_color_button.setStyleSheet( "background-color:%s" % str(plot_fill_color.name())) new_val = str(plot_fill_color.name()) + str(self.defaults['global_sel_fill'][7:9]) - self.general_defaults_form.general_group.sf_color_entry.set_value(new_val) + self.general_defaults_form.general_gui_group.sf_color_entry.set_value(new_val) self.defaults['global_sel_fill'] = new_val def on_sf_color_spinner(self): - spinner_value = self.general_defaults_form.general_group.sf_color_alpha_spinner.value() - self.general_defaults_form.general_group.sf_color_alpha_slider.setValue(spinner_value) + spinner_value = self.general_defaults_form.general_gui_group.sf_color_alpha_spinner.value() + self.general_defaults_form.general_gui_group.sf_color_alpha_slider.setValue(spinner_value) self.defaults['global_sel_fill'] = self.defaults['global_sel_fill'][:7] + \ (hex(spinner_value)[2:] if int(hex(spinner_value)[2:], 16) > 0 else '00') self.defaults['global_sel_line'] = self.defaults['global_sel_line'][:7] + \ (hex(spinner_value)[2:] if int(hex(spinner_value)[2:], 16) > 0 else '00') def on_sf_color_slider(self): - slider_value = self.general_defaults_form.general_group.sf_color_alpha_slider.value() - self.general_defaults_form.general_group.sf_color_alpha_spinner.setValue(slider_value) + slider_value = self.general_defaults_form.general_gui_group.sf_color_alpha_slider.value() + self.general_defaults_form.general_gui_group.sf_color_alpha_spinner.setValue(slider_value) def on_sl_color_entry(self): - self.defaults['global_sel_line'] = self.general_defaults_form.general_group.sl_color_entry.get_value()[:7] + \ + self.defaults['global_sel_line'] = self.general_defaults_form.general_gui_group.sl_color_entry.get_value()[:7] + \ self.defaults['global_sel_line'][7:9] - self.general_defaults_form.general_group.sl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sl_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_sel_line'])[:7]) def on_sl_color_button(self): @@ -2808,18 +2842,18 @@ class App(QtCore.QObject): if plot_line_color.isValid() is False: return - self.general_defaults_form.general_group.sl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sl_color_button.setStyleSheet( "background-color:%s" % str(plot_line_color.name())) new_val_line = str(plot_line_color.name()) + str(self.defaults['global_sel_line'][7:9]) - self.general_defaults_form.general_group.sl_color_entry.set_value(new_val_line) + self.general_defaults_form.general_gui_group.sl_color_entry.set_value(new_val_line) self.defaults['global_sel_line'] = new_val_line # Setting selection colors (right - left) handlers def on_alt_sf_color_entry(self): - self.defaults['global_alt_sel_fill'] = self.general_defaults_form.general_group \ + self.defaults['global_alt_sel_fill'] = self.general_defaults_form.general_gui_group \ .alt_sf_color_entry.get_value()[:7] + self.defaults['global_alt_sel_fill'][7:9] - self.general_defaults_form.general_group.alt_sf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.alt_sf_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_alt_sel_fill'])[:7]) def on_alt_sf_color_button(self): @@ -2831,29 +2865,29 @@ class App(QtCore.QObject): if plot_fill_color.isValid() is False: return - self.general_defaults_form.general_group.alt_sf_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.alt_sf_color_button.setStyleSheet( "background-color:%s" % str(plot_fill_color.name())) new_val = str(plot_fill_color.name()) + str(self.defaults['global_alt_sel_fill'][7:9]) - self.general_defaults_form.general_group.alt_sf_color_entry.set_value(new_val) + self.general_defaults_form.general_gui_group.alt_sf_color_entry.set_value(new_val) self.defaults['global_alt_sel_fill'] = new_val def on_alt_sf_color_spinner(self): - spinner_value = self.general_defaults_form.general_group.alt_sf_color_alpha_spinner.value() - self.general_defaults_form.general_group.alt_sf_color_alpha_slider.setValue(spinner_value) + spinner_value = self.general_defaults_form.general_gui_group.alt_sf_color_alpha_spinner.value() + self.general_defaults_form.general_gui_group.alt_sf_color_alpha_slider.setValue(spinner_value) self.defaults['global_alt_sel_fill'] = self.defaults['global_alt_sel_fill'][:7] + \ (hex(spinner_value)[2:] if int(hex(spinner_value)[2:], 16) > 0 else '00') self.defaults['global_alt_sel_line'] = self.defaults['global_alt_sel_line'][:7] + \ (hex(spinner_value)[2:] if int(hex(spinner_value)[2:], 16) > 0 else '00') def on_alt_sf_color_slider(self): - slider_value = self.general_defaults_form.general_group.alt_sf_color_alpha_slider.value() - self.general_defaults_form.general_group.alt_sf_color_alpha_spinner.setValue(slider_value) + slider_value = self.general_defaults_form.general_gui_group.alt_sf_color_alpha_slider.value() + self.general_defaults_form.general_gui_group.alt_sf_color_alpha_spinner.setValue(slider_value) def on_alt_sl_color_entry(self): - self.defaults['global_alt_sel_line'] = self.general_defaults_form.general_group \ + self.defaults['global_alt_sel_line'] = self.general_defaults_form.general_gui_group \ .alt_sl_color_entry.get_value()[:7] + self.defaults['global_alt_sel_line'][7:9] - self.general_defaults_form.general_group.alt_sl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.alt_sl_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_alt_sel_line'])[:7]) def on_alt_sl_color_button(self): @@ -2865,18 +2899,18 @@ class App(QtCore.QObject): if plot_line_color.isValid() is False: return - self.general_defaults_form.general_group.alt_sl_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.alt_sl_color_button.setStyleSheet( "background-color:%s" % str(plot_line_color.name())) new_val_line = str(plot_line_color.name()) + str(self.defaults['global_alt_sel_line'][7:9]) - self.general_defaults_form.general_group.alt_sl_color_entry.set_value(new_val_line) + self.general_defaults_form.general_gui_group.alt_sl_color_entry.set_value(new_val_line) self.defaults['global_alt_sel_line'] = new_val_line # Setting Editor colors def on_draw_color_entry(self): - self.defaults['global_draw_color'] = self.general_defaults_form.general_group \ + self.defaults['global_draw_color'] = self.general_defaults_form.general_gui_group \ .draw_color_entry.get_value() - self.general_defaults_form.general_group.draw_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.draw_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_draw_color'])) def on_draw_color_button(self): @@ -2888,17 +2922,17 @@ class App(QtCore.QObject): if draw_color.isValid() is False: return - self.general_defaults_form.general_group.draw_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.draw_color_button.setStyleSheet( "background-color:%s" % str(draw_color.name())) new_val = str(draw_color.name()) - self.general_defaults_form.general_group.draw_color_entry.set_value(new_val) + self.general_defaults_form.general_gui_group.draw_color_entry.set_value(new_val) self.defaults['global_draw_color'] = new_val def on_sel_draw_color_entry(self): - self.defaults['global_sel_draw_color'] = self.general_defaults_form.general_group \ + self.defaults['global_sel_draw_color'] = self.general_defaults_form.general_gui_group \ .sel_draw_color_entry.get_value() - self.general_defaults_form.general_group.sel_draw_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sel_draw_color_button.setStyleSheet( "background-color:%s" % str(self.defaults['global_sel_draw_color'])) def on_sel_draw_color_button(self): @@ -2910,11 +2944,11 @@ class App(QtCore.QObject): if sel_draw_color.isValid() is False: return - self.general_defaults_form.general_group.sel_draw_color_button.setStyleSheet( + self.general_defaults_form.general_gui_group.sel_draw_color_button.setStyleSheet( "background-color:%s" % str(sel_draw_color.name())) new_val_sel = str(sel_draw_color.name()) - self.general_defaults_form.general_group.sel_draw_color_entry.set_value(new_val_sel) + self.general_defaults_form.general_gui_group.sel_draw_color_entry.set_value(new_val_sel) self.defaults['global_sel_draw_color'] = new_val_sel def on_workspace_modified(self): @@ -2922,7 +2956,7 @@ class App(QtCore.QObject): self.plotcanvas.draw_workspace() def on_workspace(self): - if self.general_defaults_form.general_group.workspace_cb.isChecked(): + if self.general_defaults_form.general_gui_group.workspace_cb.isChecked(): self.plotcanvas.restore_workspace() else: self.plotcanvas.delete_workspace() @@ -2930,10 +2964,10 @@ class App(QtCore.QObject): self.save_defaults(silent=True) def on_workspace_menu(self): - if self.general_defaults_form.general_group.workspace_cb.isChecked(): - self.general_defaults_form.general_group.workspace_cb.setChecked(False) + if self.general_defaults_form.general_gui_group.workspace_cb.isChecked(): + self.general_defaults_form.general_gui_group.workspace_cb.setChecked(False) else: - self.general_defaults_form.general_group.workspace_cb.setChecked(True) + self.general_defaults_form.general_gui_group.workspace_cb.setChecked(True) self.on_workspace() def on_save_button(self): @@ -3573,6 +3607,9 @@ class App(QtCore.QObject): if event.key == 'G': self.on_fileopengerber() + if event.key == 'N': + self.on_file_new_click() + if event.key == 'M': self.measurement_tool.run() @@ -3585,14 +3622,44 @@ class App(QtCore.QObject): return elif self.key_modifiers == QtCore.Qt.AltModifier: # place holder for further shortcut key - return + if event.key == 'C': + self.calculator_tool.run() + + if event.key == 'D': + self.dblsidedtool.run() + + if event.key == 'L': + self.film_tool.run() + + if event.key == 'N': + self.ncclear_tool.run() + + if event.key == 'P': + self.paint_tool.run() + + if event.key == 'R': + self.transform_tool.run() + + if event.key == 'U': + self.cutout_tool.run() + + if event.key == 'Z': + self.panelize_tool.run() + elif self.key_modifiers == QtCore.Qt.ShiftModifier: # place holder for further shortcut key + if event.key == 'C': + self.on_copy_name() + # Toggle axis if event.key == 'G': self.on_toggle_axis() + # Open Preferences Window + if event.key == 'P': + self.on_preferences() + # Rotate Object by 90 degree CCW if event.key == 'R': self.on_rotate(silent=True, preset=-90) @@ -3601,6 +3668,14 @@ class App(QtCore.QObject): if event.key == 'W': self.on_workspace_menu() + # Skew on X axis + if event.key == 'X': + self.on_skewx() + + # Skew on Y axis + if event.key == 'Y': + self.on_skewy() + return else: if event.key == self.defaults['fit_key']: # 1 @@ -3624,9 +3699,6 @@ class App(QtCore.QObject): self.collection.get_active().ui.plot_cb.toggle() self.delete_selection_shape() - if event.key == 'C': - self.on_copy_name() - if event.key == 'E': self.object2editor() @@ -3643,12 +3715,14 @@ class App(QtCore.QObject): if event.key == 'N': self.on_new_geometry() + if event.key == 'O': + self.on_set_origin() + + if event.key == 'P': + self.properties_tool.run() + if event.key == 'Q': - if self.options["units"] == 'MM': - self.general_options_form.general_group.units_radio.set_value("IN") - else: - self.general_options_form.general_group.units_radio.set_value("MM") - self.on_toggle_units() + self.on_toggle_units_click() if event.key == 'R': self.on_rotate(silent=True, preset=90) @@ -3656,9 +3730,6 @@ class App(QtCore.QObject): if event.key == 'S': self.on_toggle_shell() - if event.key == 'T': - self.transform_tool.run() - if event.key == 'V': self.on_zoom_fit(None) @@ -3695,7 +3766,6 @@ class App(QtCore.QObject): 2: Zoom Out
3: Zoom In
A: Draw an Arc (when in Edit Mode)
-C: Copy Obj_Name
C: Copy Geo Item (when in Edit Mode)
E: Edit Object (if selected)
G: Grid On/Off
@@ -3704,13 +3774,14 @@ class App(QtCore.QObject): M: Move Geo Item (when in Edit Mode)
N: New Geometry
N: Draw a Polygon (when in Edit Mode)
+O: Set Origin
O: Draw a Circle (when in Edit Mode)
Q: Change Units
+P: Open Properties Tool
P: Draw a Path (when in Edit Mode)
R: Rotate by 90 degree CW
R: Draw Rectangle (when in Edit Mode)
S: Shell Toggle
-T: Transformation
V: View Fit
X: Flip on X_axis
Y: Flip on Y_axis
@@ -3720,14 +3791,28 @@ class App(QtCore.QObject): CTRL+C: Copy Obj
CTRL+E: Open Excellon File
CTRL+G: Open Gerber File
+CTRL+N: New Project
CTRL+M: Measurement Tool
CTRL+O: Open Project
CTRL+S: Save Project As
CTRL+S: Save Object and Exit Editor (when in Edit Mode)

+SHIFT+C: Copy Obj_Name
SHIFT+G: Toggle the axis
+SHIFT+P: Open Preferences Window
SHIFT+R: Rotate by 90 degree CCW
SHIFT+W: Toggle the workspace
+SHIFT+X: Skew on X axis
+SHIFT+Y: Skew on Y axis
+
+ALT+C: Calculators Tool
+ALT+D: 2-Sided PCB Tool
+ALT+L: Film PCB Tool
+ALT+N: Non-Copper Clearing Tool
+ALT+P: Paint Area Tool
+ALT+R: Transformation Tool
+ALT+U: Cutout PCB Tool
+ALT+Z: Panelize PCB Tool
Del: Delete Obj''' helpbox = QtWidgets.QMessageBox() @@ -3740,7 +3825,13 @@ class App(QtCore.QObject): def on_copy_name(self): obj = self.collection.get_active() - name = obj.options["name"] + try: + name = obj.options["name"] + except AttributeError: + log.debug("on_copy_name() --> No object selected to copy it's name") + self.inform.emit("[warning_notcl]No object selected to copy it's name") + return + self.clipboard.setText(name) self.inform.emit("Name copied on clipboard ...") @@ -4093,13 +4184,16 @@ class App(QtCore.QObject): "Do you want to Save the project?") msgbox.setWindowTitle("Save changes") msgbox.setWindowIcon(QtGui.QIcon('share/save_as.png')) - msgbox.setStandardButtons(QtWidgets.QMessageBox.Cancel | QtWidgets.QMessageBox.Ok) + msgbox.setStandardButtons(QtWidgets.QMessageBox.Cancel | QtWidgets.QMessageBox.Yes | + QtWidgets.QMessageBox.No) msgbox.setDefaultButton(QtWidgets.QMessageBox.Ok) response = msgbox.exec_() - if response == QtWidgets.QMessageBox.Ok: + if response == QtWidgets.QMessageBox.Yes: self.on_file_saveprojectas() + elif response == QtWidgets.QMessageBox.Cancel: + return self.on_file_new() else: self.on_file_new() @@ -4963,7 +5057,7 @@ class App(QtCore.QObject): return "Could not retrieve object: %s" % obj_name # updated units - units = self.general_options_form.general_group.units_radio.get_value().upper() + units = self.general_options_form.general_app_group.units_radio.get_value().upper() if units == 'IN' or units == 'INCH': units = 'INCH' @@ -5056,7 +5150,7 @@ class App(QtCore.QObject): return "Could not retrieve object: %s" % obj_name # updated units - units = self.general_options_form.general_group.units_radio.get_value().upper() + units = self.general_options_form.general_app_group.units_radio.get_value().upper() if units == 'IN' or units == 'INCH': units = 'INCH' elif units == 'MM' or units == 'METIRC': @@ -5109,7 +5203,7 @@ class App(QtCore.QObject): "Only Geometry and Gerber are supported") return - units = self.general_options_form.general_group.units_radio.get_value().upper() + units = self.general_options_form.general_app_group.units_radio.get_value().upper() def obj_init(geo_obj, app_obj): geo_obj.import_svg(filename, obj_type, units=units) @@ -5150,7 +5244,7 @@ class App(QtCore.QObject): "Only Geometry and Gerber are supported") return - units = self.general_options_form.general_group.units_radio.get_value().upper() + units = self.general_options_form.general_app_group.units_radio.get_value().upper() def obj_init(geo_obj, app_obj): geo_obj.import_dxf(filename, obj_type, units=units) @@ -5197,7 +5291,7 @@ class App(QtCore.QObject): # Object name name = outname or filename.split('/')[-1].split('\\')[-1] - units = self.general_options_form.general_group.units_radio.get_value() + units = self.general_options_form.general_app_group.units_radio.get_value() self.new_object(obj_type, name, obj_init) self.progress.emit(20) @@ -5886,7 +5980,7 @@ class App(QtCore.QObject): self.log.debug("version_check()") - if self.general_defaults_form.general_group.send_stats_cb.get_value() is True: + if self.general_defaults_form.general_gui_group.send_stats_cb.get_value() is True: full_url = App.version_url + \ "?s=" + str(self.defaults['global_serial']) + \ "&v=" + str(self.version) + \ diff --git a/FlatCAMEditor.py b/FlatCAMEditor.py index bc3264a9..e497db5d 100644 --- a/FlatCAMEditor.py +++ b/FlatCAMEditor.py @@ -291,7 +291,7 @@ class TextInputTool(FlatCAMTool): font_name=self.font_name, font_size=font_to_geo_size, font_type=font_to_geo_type, - units=self.app.general_options_form.general_group.units_radio.get_value().upper()) + units=self.app.general_options_form.general_app_group.units_radio.get_value().upper()) def font_family(self, font): self.text_input_entry.selectAll() @@ -1143,6 +1143,7 @@ class FCMove(FCShapeTool): self.start_msg = "Click on reference point." def set_origin(self, origin): + self.draw_app.app.inform.emit("Click on destination point.") self.origin = origin def click(self, point): @@ -1901,6 +1902,9 @@ class FlatCAMGeoEditor(QtCore.QObject): self.app.ui.geo_cutpath_btn.triggered.connect(self.cutpath) self.app.ui.geo_delete_btn.triggered.connect(self.on_delete_btn) + self.app.ui.geo_move_menuitem.triggered.connect(self.on_move) + self.app.ui.geo_cornersnap_menuitem.triggered.connect(self.on_corner_snap) + ## Toolbar events and properties self.tools = { "select": {"button": self.app.ui.geo_select_btn, @@ -2596,14 +2600,11 @@ class FlatCAMGeoEditor(QtCore.QObject): # Corner Snap if event.key.name == 'K': - self.app.ui.corner_snap_btn.trigger() + self.on_corner_snap() # Move if event.key.name == 'M': - self.app.ui.geo_move_btn.setChecked(True) - self.on_tool_select('move') - self.active_tool.set_origin(self.snap(self.x, self.y)) - self.app.inform.emit("Click on target point.") + self.on_move_click() # Polygon Tool if event.key.name == 'N': @@ -2718,6 +2719,17 @@ class FlatCAMGeoEditor(QtCore.QObject): if shape in self.selected: self.selected.remove(shape) # TODO: Check performance + def on_move(self): + self.app.ui.geo_move_btn.setChecked(True) + self.on_tool_select('move') + + def on_move_click(self): + self.on_move() + self.active_tool.set_origin(self.snap(self.x, self.y)) + + def on_corner_snap(self): + self.app.ui.corner_snap_btn.trigger() + def get_selected(self): """ Returns list of shapes that are selected in the editor. @@ -3638,7 +3650,7 @@ class FlatCAMExcEditor(QtCore.QObject): self.move_timer.setSingleShot(True) ## Current application units in Upper Case - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() self.key = None # Currently pressed key self.modifiers = None @@ -3712,7 +3724,7 @@ class FlatCAMExcEditor(QtCore.QObject): def set_ui(self): # updated units - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() self.olddia_newdia.clear() self.tool2tooldia.clear() @@ -3752,7 +3764,7 @@ class FlatCAMExcEditor(QtCore.QObject): pass # updated units - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() # make a new name for the new Excellon object (the one with edited content) self.edited_obj_name = self.exc_obj.options['name'] diff --git a/FlatCAMGUI.py b/FlatCAMGUI.py index 4a8852b8..d0b19797 100644 --- a/FlatCAMGUI.py +++ b/FlatCAMGUI.py @@ -36,22 +36,24 @@ class FlatCAMGUI(QtWidgets.QMainWindow): self.menufile = self.menu.addMenu('&File') # New - self.menufilenew = QtWidgets.QAction(QtGui.QIcon('share/file16.png'), '&New Project', self) + self.menufilenew = QtWidgets.QAction(QtGui.QIcon('share/file16.png'), '&New Project ...\tCTRL+N', self) self.menufile.addAction(self.menufilenew) self.menufile_open = self.menufile.addMenu(QtGui.QIcon('share/folder32_bis.png'), 'Open') # Open gerber ... - self.menufileopengerber = QtWidgets.QAction(QtGui.QIcon('share/flatcam_icon24.png'), 'Open &Gerber ...', self) + self.menufileopengerber = QtWidgets.QAction(QtGui.QIcon('share/flatcam_icon24.png'), + 'Open &Gerber ...\tCTRL+G', self) self.menufile_open.addAction(self.menufileopengerber) # Open gerber with follow... self.menufileopengerber_follow = QtWidgets.QAction(QtGui.QIcon('share/flatcam_icon24.png'), - 'Open &Gerber (w/ Follow)', self) + 'Open &Gerber (w/ Follow) ...', self) self.menufile_open.addAction(self.menufileopengerber_follow) self.menufile_open.addSeparator() # Open Excellon ... - self.menufileopenexcellon = QtWidgets.QAction(QtGui.QIcon('share/open_excellon32.png'), 'Open &Excellon ...', + self.menufileopenexcellon = QtWidgets.QAction(QtGui.QIcon('share/open_excellon32.png'), + 'Open &Excellon ...\tCTRL+E', self) self.menufile_open.addAction(self.menufileopenexcellon) @@ -70,7 +72,7 @@ class FlatCAMGUI(QtWidgets.QMainWindow): self.menufile.addSeparator() # Run Scripts - self.menufilerunscript = QtWidgets.QAction(QtGui.QIcon('share/script16.png'), 'Run Script', self) + self.menufilerunscript = QtWidgets.QAction(QtGui.QIcon('share/script16.png'), 'Run Script ...', self) self.menufile.addAction(self.menufilerunscript) # Separator @@ -79,18 +81,18 @@ class FlatCAMGUI(QtWidgets.QMainWindow): # Import ... self.menufileimport = self.menufile.addMenu(QtGui.QIcon('share/import.png'), 'Import') self.menufileimportsvg = QtWidgets.QAction(QtGui.QIcon('share/svg16.png'), - '&SVG as Geometry Object', self) + '&SVG as Geometry Object ...', self) self.menufileimport.addAction(self.menufileimportsvg) self.menufileimportsvg_as_gerber = QtWidgets.QAction(QtGui.QIcon('share/svg16.png'), - '&SVG as Gerber Object', self) + '&SVG as Gerber Object ...', self) self.menufileimport.addAction(self.menufileimportsvg_as_gerber) self.menufileimport.addSeparator() self.menufileimportdxf = QtWidgets.QAction(QtGui.QIcon('share/dxf16.png'), - '&DXF as Geometry Object', self) + '&DXF as Geometry Object ...', self) self.menufileimport.addAction(self.menufileimportdxf) self.menufileimportdxf_as_gerber = QtWidgets.QAction(QtGui.QIcon('share/dxf16.png'), - '&DXF as Gerber Object', self) + '&DXF as Gerber Object ...', self) self.menufileimport.addAction(self.menufileimportdxf_as_gerber) self.menufileimport.addSeparator() @@ -128,11 +130,12 @@ class FlatCAMGUI(QtWidgets.QMainWindow): self.menufile_save = self.menufile.addMenu(QtGui.QIcon('share/save_as.png'), 'Save') # Save Project - self.menufilesaveproject = QtWidgets.QAction(QtGui.QIcon('share/floppy16.png'), '&Save Project', self) + self.menufilesaveproject = QtWidgets.QAction(QtGui.QIcon('share/floppy16.png'), '&Save Project ...', self) self.menufile_save.addAction(self.menufilesaveproject) # Save Project As ... - self.menufilesaveprojectas = QtWidgets.QAction(QtGui.QIcon('share/save_as.png'), 'Save Project &As ...', self) + self.menufilesaveprojectas = QtWidgets.QAction(QtGui.QIcon('share/save_as.png'), + 'Save Project &As ...\tCTRL+S', self) self.menufile_save.addAction(self.menufilesaveprojectas) # Save Project Copy ... @@ -151,12 +154,12 @@ class FlatCAMGUI(QtWidgets.QMainWindow): ### Edit ### self.menuedit = self.menu.addMenu('&Edit') - self.menueditnew = self.menuedit.addAction(QtGui.QIcon('share/new_geo16.png'), '&New Geometry') - self.menueditnewexc = self.menuedit.addAction(QtGui.QIcon('share/new_geo16.png'), 'New Excellon') + self.menueditnew = self.menuedit.addAction(QtGui.QIcon('share/new_geo16.png'), '&New Geometry\tN') + self.menueditnewexc = self.menuedit.addAction(QtGui.QIcon('share/new_geo16.png'), 'New Excellon\tX') # Separator self.menuedit.addSeparator() - self.menueditedit = self.menuedit.addAction(QtGui.QIcon('share/edit16.png'), 'Edit Object') - self.menueditok = self.menuedit.addAction(QtGui.QIcon('share/edit_ok16.png'), '&Update Object') + self.menueditedit = self.menuedit.addAction(QtGui.QIcon('share/edit16.png'), 'Edit Object\tE') + self.menueditok = self.menuedit.addAction(QtGui.QIcon('share/edit_ok16.png'), '&Update Object\tCTRL+S') # Separator self.menuedit.addSeparator() self.menuedit_convert = self.menuedit.addMenu(QtGui.QIcon('share/convert24.png'), 'Conversion') @@ -185,29 +188,31 @@ class FlatCAMGUI(QtWidgets.QMainWindow): "Will convert a Geometry object from multi_geometry type\n" "to a single_geometry type.") self.menuedit_convert.setToolTipsVisible(True) - # Separator - self.menuedit.addSeparator() - self.menueditdelete = self.menuedit.addAction(QtGui.QIcon('share/trash16.png'), '&Delete') # Separator self.menuedit.addSeparator() - self.menueditcopyobject = self.menuedit.addAction(QtGui.QIcon('share/copy.png'), '&Copy Object') + self.menueditcopyobject = self.menuedit.addAction(QtGui.QIcon('share/copy.png'), '&Copy Object\tCTRL+C') self.menueditcopyobjectasgeom = self.menuedit.addAction(QtGui.QIcon('share/copy_geo.png'), 'Copy as &Geom') + # Separator + self.menuedit.addSeparator() + self.menueditdelete = self.menuedit.addAction(QtGui.QIcon('share/trash16.png'), '&Delete\tDEL') # Separator self.menuedit.addSeparator() - self.menueditorigin = self.menuedit.addAction(QtGui.QIcon('share/origin.png'), 'Se&t Origin') - self.menueditjump = self.menuedit.addAction(QtGui.QIcon('share/jump_to16.png'), 'Jump to Location') + self.menueditorigin = self.menuedit.addAction(QtGui.QIcon('share/origin.png'), 'Se&t Origin\tO') + self.menueditjump = self.menuedit.addAction(QtGui.QIcon('share/jump_to16.png'), 'Jump to Location\tJ') # Separator self.menuedit.addSeparator() + self.menuedittoggleunits= self.menuedit.addAction(QtGui.QIcon('share/toggle_units16.png'), + 'Toggle Units\tQ') self.menueditselectall = self.menuedit.addAction(QtGui.QIcon('share/select_all.png'), - '&Select All') + '&Select All\tCTRL+A') # Separator self.menuedit.addSeparator() - self.menueditpreferences = self.menuedit.addAction(QtGui.QIcon('share/pref.png'), '&Preferences') + self.menueditpreferences = self.menuedit.addAction(QtGui.QIcon('share/pref.png'), '&Preferences\tSHIFT+P') ### Options ### self.menuoptions = self.menu.addMenu('&Options') @@ -225,21 +230,21 @@ class FlatCAMGUI(QtWidgets.QMainWindow): # self.menuoptions_transform = self.menuoptions.addMenu(QtGui.QIcon('share/transform.png'), # '&Transform Object') self.menuoptions_transform_rotate = self.menuoptions.addAction(QtGui.QIcon('share/rotate.png'), - "&Rotate Selection") + "&Rotate Selection\tSHIFT+(R)") # Separator self.menuoptions.addSeparator() self.menuoptions_transform_skewx = self.menuoptions.addAction(QtGui.QIcon('share/skewX.png'), - "&Skew on X axis") + "&Skew on X axis\tSHIFT+X") self.menuoptions_transform_skewy = self.menuoptions.addAction(QtGui.QIcon('share/skewY.png'), - "S&kew on Y axis") + "S&kew on Y axis\tSHIFT+Y") # Separator self.menuoptions.addSeparator() self.menuoptions_transform_flipx = self.menuoptions.addAction(QtGui.QIcon('share/flipx.png'), - "Flip on &X axis") + "Flip on &X axis\tX") self.menuoptions_transform_flipy = self.menuoptions.addAction(QtGui.QIcon('share/flipy.png'), - "Flip on &Y axis") + "Flip on &Y axis\tY") # Separator self.menuoptions.addSeparator() @@ -252,14 +257,15 @@ class FlatCAMGUI(QtWidgets.QMainWindow): 'Disable non-selected') # Separator self.menuview.addSeparator() - self.menuview_zoom_fit = self.menuview.addAction(QtGui.QIcon('share/zoom_fit32.png'), "&Zoom Fit") - self.menuview_zoom_in = self.menuview.addAction(QtGui.QIcon('share/zoom_in32.png'), "&Zoom In") - self.menuview_zoom_out = self.menuview.addAction(QtGui.QIcon('share/zoom_out32.png'), "&Zoom Out") + self.menuview_zoom_fit = self.menuview.addAction(QtGui.QIcon('share/zoom_fit32.png'), "&Zoom Fit\t1") + self.menuview_zoom_in = self.menuview.addAction(QtGui.QIcon('share/zoom_in32.png'), "&Zoom In\t2") + self.menuview_zoom_out = self.menuview.addAction(QtGui.QIcon('share/zoom_out32.png'), "&Zoom Out\t3") self.menuview.addSeparator() - self.menuview_toggle_axis = self.menuview.addAction(QtGui.QIcon('share/axis32.png'), "&Toggle Axis") + self.menuview_toggle_grid = self.menuview.addAction(QtGui.QIcon('share/grid32.png'), "&Toggle Grid\tG") + self.menuview_toggle_axis = self.menuview.addAction(QtGui.QIcon('share/axis32.png'), "&Toggle Axis\tSHIFT+G") self.menuview_toggle_workspace = self.menuview.addAction(QtGui.QIcon('share/workspace24.png'), - "Toggle Workspace") + "Toggle Workspace\tSHIFT+W") ### FlatCAM Editor menu ### @@ -269,28 +275,46 @@ class FlatCAMGUI(QtWidgets.QMainWindow): self.menu.addMenu(self.geo_editor_menu) # self.select_menuitem = self.menu.addAction(QtGui.QIcon('share/pointer16.png'), "Select 'Esc'") - self.geo_add_circle_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/circle32.png'), 'Add Circle') - self.geo_add_arc_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/arc16.png'), 'Add Arc') + self.geo_add_circle_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/circle32.png'), 'Add Circle\tO' + ) + self.geo_add_arc_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/arc16.png'), 'Add Arc\tA') self.geo_editor_menu.addSeparator() - self.geo_add_rectangle_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/rectangle32.png'), 'Add Rectangle') - self.geo_add_polygon_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/polygon32.png'), 'Add Polygon') - self.geo_add_path_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/path32.png'), 'Add Path') + self.geo_add_rectangle_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/rectangle32.png'), 'Add Rectangle\tR' + ) + self.geo_add_polygon_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/polygon32.png'), 'Add Polygon\tN' + ) + self.geo_add_path_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/path32.png'), 'Add Path\tP') self.geo_editor_menu.addSeparator() - self.geo_add_text_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/text32.png'), 'Add Text') + self.geo_add_text_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/text32.png'), 'Add Text\tT') self.geo_editor_menu.addSeparator() self.geo_union_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/union16.png'), 'Polygon Union') self.geo_intersection_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/intersection16.png'), 'Polygon Intersection') - self.geo_subtract_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/subtract16.png'), 'Polygon Subtraction') + self.geo_subtract_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/subtract16.png'), 'Polygon Subtraction' + ) self.geo_editor_menu.addSeparator() - self.geo_cutpath_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/cutpath16.png'), 'Cut Path') + self.geo_cutpath_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/cutpath16.png'), 'Cut Path\tX') # self.move_menuitem = self.menu.addAction(QtGui.QIcon('share/move16.png'), "Move Objects 'm'") - self.geo_copy_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/copy16.png'), "Copy Geom") - self.geo_delete_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/deleteshape16.png'), "Delete Shape") + self.geo_copy_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/copy16.png'), "Copy Geom\tC") + self.geo_delete_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/deleteshape16.png'), "Delete Shape\tDEL" + ) self.geo_editor_menu.addSeparator() - self.geo_buffer_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/buffer16.png'), "Buffer Selection") - self.geo_paint_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/paint16.png'), "Paint Selection") + self.geo_move_menuitem = self.geo_editor_menu.addAction(QtGui.QIcon('share/move32.png'), "Move\tM") + self.geo_buffer_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/buffer16.png'), "Buffer Selection\tB" + ) + self.geo_paint_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/paint16.png'), "Paint Selection\tI" + ) self.geo_editor_menu.addSeparator() + self.geo_cornersnap_menuitem = self.geo_editor_menu.addAction( + QtGui.QIcon('share/corner32.png'), "Toggle Corner Snap\tK" + ) # self.exc_editor_menu = QtWidgets.QMenu("Excellon Editor") # self.menu.addMenu(self.exc_editor_menu) @@ -302,7 +326,7 @@ class FlatCAMGUI(QtWidgets.QMainWindow): # self.menutool = self.menu.addMenu('&Tool') self.menutool = QtWidgets.QMenu('&Tool') self.menutoolaction = self.menu.addMenu(self.menutool) - self.menutoolshell = self.menutool.addAction(QtGui.QIcon('share/shell16.png'), '&Command Line') + self.menutoolshell = self.menutool.addAction(QtGui.QIcon('share/shell16.png'), '&Command Line\tS') ### Help ### self.menuhelp = self.menu.addMenu('&Help') @@ -655,6 +679,8 @@ class FlatCAMGUI(QtWidgets.QMainWindow): self.draw_line = self.g_editor_cmenu.addAction(QtGui.QIcon('share/path32.png'), "Line") self.draw_rect = self.g_editor_cmenu.addAction(QtGui.QIcon('share/rectangle32.png'), "Rectangle") self.draw_cut = self.g_editor_cmenu.addAction(QtGui.QIcon('share/cutpath32.png'), "Cut") + self.g_editor_cmenu.addSeparator() + self.draw_move = self.g_editor_cmenu.addAction(QtGui.QIcon('share/move32.png'), "Move") self.e_editor_cmenu = self.popMenu.addMenu(QtGui.QIcon('share/drill32.png'), "Exc Editor") self.drill = self.e_editor_cmenu.addAction(QtGui.QIcon('share/drill32.png'), "Add Drill") @@ -844,18 +870,29 @@ class FlatCAMGUI(QtWidgets.QMainWindow): # self.splitter.sizes()[0] is actually the size of the "notebook" self.geom_update.emit(grect.x(), grect.y(), grect.width(), grect.height(), self.splitter.sizes()[0]) self.final_save.emit() - QtWidgets.qApp.quit() + + if self.app.should_we_quit is True: + QtWidgets.qApp.quit() + else: + self.app.should_we_quit = True + event.ignore() class GeneralPreferencesUI(QtWidgets.QWidget): def __init__(self, parent=None): QtWidgets.QWidget.__init__(self, parent=parent) - self.layout = QtWidgets.QVBoxLayout() + self.layout = QtWidgets.QHBoxLayout() self.setLayout(self.layout) - self.general_group = GeneralPrefGroupUI() - self.general_group.setFixedWidth(260) - self.layout.addWidget(self.general_group) + self.general_app_group = GeneralAppPrefGroupUI() + self.general_app_group.setFixedWidth(260) + + self.general_gui_group = GeneralGUIPrefGroupUI() + self.general_gui_group.setFixedWidth(260) + + self.layout.addWidget(self.general_app_group) + self.layout.addWidget(self.general_gui_group) + self.layout.addStretch() class GerberPreferencesUI(QtWidgets.QWidget): @@ -922,59 +959,15 @@ class OptionsGroupUI(QtWidgets.QGroupBox): self.setLayout(self.layout) -class GeneralPrefGroupUI(OptionsGroupUI): +class GeneralGUIPrefGroupUI(OptionsGroupUI): def __init__(self, parent=None): - super(GeneralPrefGroupUI, self).__init__(self) + super(GeneralGUIPrefGroupUI, self).__init__(self) - self.setTitle(str("Global Preferences")) + self.setTitle(str("GUI Preferences")) # Create a form layout for the Application general settings self.form_box = QtWidgets.QFormLayout() - # Units for FlatCAM - self.unitslabel = QtWidgets.QLabel('Units:') - self.unitslabel.setToolTip("Those are units in which FlatCAM works.") - self.units_radio = RadioSet([{'label': 'IN', 'value': 'IN'}, - {'label': 'MM', 'value': 'MM'}]) - - # Shell StartUp CB - self.shell_startup_label = QtWidgets.QLabel('Shell at StartUp:') - self.shell_startup_label.setToolTip( - "Check this box if you want the shell to\n" - "start automatically at startup." - ) - self.shell_startup_cb = FCCheckBox(label='') - self.shell_startup_cb.setToolTip( - "Check this box if you want the shell to\n" - "start automatically at startup." - ) - - # Version Check CB - self.version_check_label = QtWidgets.QLabel('Version Check:') - self.version_check_label.setToolTip( - "Check this box if you want to check\n" - "for a new version automatically at startup." - ) - self.version_check_cb = FCCheckBox(label='') - self.version_check_cb.setToolTip( - "Check this box if you want to check\n" - "for a new version automatically at startup." - ) - - # Send Stats CB - self.send_stats_label = QtWidgets.QLabel('Send Stats:') - self.send_stats_label.setToolTip( - "Check this box if you agree to send anonymous\n" - "stats automatically at startup, to help improve FlatCAM." - ) - self.send_stats_cb= FCCheckBox(label='') - self.send_stats_cb.setToolTip( - "Check this box if you agree to send anonymous\n" - "stats automatically at startup, to help improve FlatCAM." - ) - - self.ois_version_check = OptionalInputSection(self.version_check_cb, [self.send_stats_cb]) - # Grid X Entry self.gridx_label = QtWidgets.QLabel('Grid X value:') self.gridx_label.setToolTip( @@ -989,30 +982,6 @@ class GeneralPrefGroupUI(OptionsGroupUI): ) self.gridy_entry = LengthEntry() - # Select mouse pan button - self.panbuttonlabel = QtWidgets.QLabel('Pan Button:') - self.panbuttonlabel.setToolTip("Select the mouse button to use for panning.") - self.pan_button_radio = RadioSet([{'label': 'Middle But.', 'value': '3'}, - {'label': 'Right But.', 'value': '2'}]) - - # Multiple Selection Modifier Key - self.mselectlabel = QtWidgets.QLabel('Multiple Sel:') - self.mselectlabel.setToolTip("Select the key used for multiple selection.") - self.mselect_radio = RadioSet([{'label': 'CTRL', 'value': 'Control'}, - {'label': 'SHIFT', 'value': 'Shift'}]) - - # # Mouse panning with "Space" key, CB - # self.pan_with_space_label = QtWidgets.QLabel('Pan w/ Space:') - # self.pan_with_space_label.setToolTip( - # "Check this box if you want to pan when mouse is moved,\n" - # "and key 'Space' is pressed." - # ) - # self.pan_with_space_cb = FCCheckBox(label='') - # self.pan_with_space_cb.setToolTip( - # "Check this box if you want to pan when mouse is moved,\n" - # "and key 'Space' is pressed." - # ) - # Workspace self.workspace_lbl = QtWidgets.QLabel('Workspace:') self.workspace_lbl.setToolTip( @@ -1214,17 +1183,12 @@ class GeneralPrefGroupUI(OptionsGroupUI): self.spacelabel = QtWidgets.QLabel('') # Add (label - input field) pair to the QFormLayout - self.form_box.addRow(self.unitslabel, self.units_radio) + self.form_box.addRow(self.spacelabel, self.spacelabel) - self.form_box.addRow(self.shell_startup_label, self.shell_startup_cb) - self.form_box.addRow(self.version_check_label, self.version_check_cb) - self.form_box.addRow(self.send_stats_label, self.send_stats_cb) self.form_box.addRow(self.gridx_label, self.gridx_entry) self.form_box.addRow(self.gridy_label, self.gridy_entry) - self.form_box.addRow(self.panbuttonlabel, self.pan_button_radio) - self.form_box.addRow(self.mselectlabel, self.mselect_radio) - # self.form_box.addRow(self.pan_with_space_label, self.pan_with_space_cb) + self.form_box.addRow(self.workspace_lbl, self.workspace_cb) self.form_box.addRow(self.workspace_type_lbl, self.wk_cb) self.form_box.addRow(self.spacelabel, self.spacelabel) @@ -1245,6 +1209,114 @@ class GeneralPrefGroupUI(OptionsGroupUI): self.layout.addLayout(self.form_box) +class GeneralAppPrefGroupUI(OptionsGroupUI): + def __init__(self, parent=None): + super(GeneralAppPrefGroupUI, self).__init__(self) + + self.setTitle(str("App Preferences")) + + # Create a form layout for the Application general settings + self.form_box = QtWidgets.QFormLayout() + + # Units for FlatCAM + self.unitslabel = QtWidgets.QLabel('Units:') + self.unitslabel.setToolTip("Those are units in which FlatCAM works.") + self.units_radio = RadioSet([{'label': 'IN', 'value': 'IN'}, + {'label': 'MM', 'value': 'MM'}]) + + # Languages for FlatCAM + self.languagelabel = QtWidgets.QLabel('Languages:') + self.languagelabel.setToolTip("Set the language used for FlatCAM texts.") + self.language_cb = FCComboBox() + self.languagespace = QtWidgets.QLabel('') + self.language_apply_btn = FCButton("Apply Language") + + # Shell StartUp CB + self.shell_startup_label = QtWidgets.QLabel('Shell at StartUp:') + self.shell_startup_label.setToolTip( + "Check this box if you want the shell to\n" + "start automatically at startup." + ) + self.shell_startup_cb = FCCheckBox(label='') + self.shell_startup_cb.setToolTip( + "Check this box if you want the shell to\n" + "start automatically at startup." + ) + + # Version Check CB + self.version_check_label = QtWidgets.QLabel('Version Check:') + self.version_check_label.setToolTip( + "Check this box if you want to check\n" + "for a new version automatically at startup." + ) + self.version_check_cb = FCCheckBox(label='') + self.version_check_cb.setToolTip( + "Check this box if you want to check\n" + "for a new version automatically at startup." + ) + + # Send Stats CB + self.send_stats_label = QtWidgets.QLabel('Send Stats:') + self.send_stats_label.setToolTip( + "Check this box if you agree to send anonymous\n" + "stats automatically at startup, to help improve FlatCAM." + ) + self.send_stats_cb= FCCheckBox(label='') + self.send_stats_cb.setToolTip( + "Check this box if you agree to send anonymous\n" + "stats automatically at startup, to help improve FlatCAM." + ) + + self.ois_version_check = OptionalInputSection(self.version_check_cb, [self.send_stats_cb]) + + # Select mouse pan button + self.panbuttonlabel = QtWidgets.QLabel('Pan Button:') + self.panbuttonlabel.setToolTip("Select the mouse button to use for panning.") + self.pan_button_radio = RadioSet([{'label': 'Middle But.', 'value': '3'}, + {'label': 'Right But.', 'value': '2'}]) + + # Multiple Selection Modifier Key + self.mselectlabel = QtWidgets.QLabel('Multiple Sel:') + self.mselectlabel.setToolTip("Select the key used for multiple selection.") + self.mselect_radio = RadioSet([{'label': 'CTRL', 'value': 'Control'}, + {'label': 'SHIFT', 'value': 'Shift'}]) + + # # Mouse panning with "Space" key, CB + # self.pan_with_space_label = QtWidgets.QLabel('Pan w/ Space:') + # self.pan_with_space_label.setToolTip( + # "Check this box if you want to pan when mouse is moved,\n" + # "and key 'Space' is pressed." + # ) + # self.pan_with_space_cb = FCCheckBox(label='') + # self.pan_with_space_cb.setToolTip( + # "Check this box if you want to pan when mouse is moved,\n" + # "and key 'Space' is pressed." + # ) + + + # Just to add empty rows + self.spacelabel = QtWidgets.QLabel('') + + # Add (label - input field) pair to the QFormLayout + self.form_box.addRow(self.unitslabel, self.units_radio) + self.form_box.addRow(self.languagelabel, self.language_cb) + self.form_box.addRow(self.languagespace, self.language_apply_btn) + + self.form_box.addRow(self.spacelabel, self.spacelabel) + self.form_box.addRow(self.shell_startup_label, self.shell_startup_cb) + self.form_box.addRow(self.version_check_label, self.version_check_cb) + self.form_box.addRow(self.send_stats_label, self.send_stats_cb) + + self.form_box.addRow(self.panbuttonlabel, self.pan_button_radio) + self.form_box.addRow(self.mselectlabel, self.mselect_radio) + # self.form_box.addRow(self.pan_with_space_label, self.pan_with_space_cb) + self.form_box.addRow(self.spacelabel, self.spacelabel) + + # Add the QFormLayout that holds the Application general defaults + # to the main layout of this TAB + self.layout.addLayout(self.form_box) + + class GerberPrefGroupUI(OptionsGroupUI): def __init__(self, parent=None): # OptionsGroupUI.__init__(self, "Gerber Options", parent=parent) diff --git a/FlatCAMObj.py b/FlatCAMObj.py index a82ee97e..62bcd6c5 100644 --- a/FlatCAMObj.py +++ b/FlatCAMObj.py @@ -1295,7 +1295,7 @@ class FlatCAMExcellon(FlatCAMObj, Excellon): """ excellon_code = '' - units = self.app.general_options_form.general_group.units_radio.get_value().upper() + units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() # store here if the file has slots, return 1 if any slots, 0 if only drills has_slots = 0 @@ -1355,7 +1355,7 @@ class FlatCAMExcellon(FlatCAMObj, Excellon): """ excellon_code = '' - units = self.app.general_options_form.general_group.units_radio.get_value().upper() + units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() # store here if the file has slots, return 1 if any slots, 0 if only drills has_slots = 0 @@ -2862,7 +2862,7 @@ class FlatCAMGeometry(FlatCAMObj, Geometry): self.ui.geo_tools_table.setCurrentItem(self.ui.geo_tools_table.item(row, 0)) def export_dxf(self): - units = self.app.general_options_form.general_group.units_radio.get_value().upper() + units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() dwg = None try: dwg = ezdxf.new('R2010') diff --git a/FlatCAMTool.py b/FlatCAMTool.py index bbc67812..585f9fa1 100644 --- a/FlatCAMTool.py +++ b/FlatCAMTool.py @@ -33,7 +33,7 @@ class FlatCAMTool(QtWidgets.QWidget): self.menuAction = None - def install(self, icon=None, separator=None, **kwargs): + def install(self, icon=None, separator=None, shortcut=None, **kwargs): before = None # 'pos' is the menu where the Action has to be installed @@ -54,8 +54,13 @@ class FlatCAMTool(QtWidgets.QWidget): # if provided, add an icon to this Action if icon is not None: self.menuAction.setIcon(icon) + # set the text name of the Action, which will be displayed in the menu - self.menuAction.setText(self.toolName) + if shortcut is None: + self.menuAction.setText(self.toolName) + else: + self.menuAction.setText(self.toolName + '\t%s' % shortcut) + # add a ToolTip to the new Action # self.menuAction.setToolTip(self.toolTip) # currently not available diff --git a/ObjectCollection.py b/ObjectCollection.py index 6e7190a1..359bf880 100644 --- a/ObjectCollection.py +++ b/ObjectCollection.py @@ -262,6 +262,9 @@ class ObjectCollection(QtCore.QAbstractItemModel): if key == QtCore.Qt.Key_G: self.app.on_fileopengerber() + if key == QtCore.Qt.Key_N: + self.app.on_file_new_click() + if key == QtCore.Qt.Key_M: self.app.measurement_tool.run() if key == QtCore.Qt.Key_O: @@ -272,6 +275,11 @@ class ObjectCollection(QtCore.QAbstractItemModel): return elif modifiers == QtCore.Qt.ShiftModifier: + # Copy Object Name + # Copy Object Name + if key == QtCore.Qt.Key_C: + self.app.on_copy_name() + # Toggle axis if key == QtCore.Qt.Key_G: if self.toggle_axis is False: @@ -286,11 +294,51 @@ class ObjectCollection(QtCore.QAbstractItemModel): self.appplotcanvas.redraw() self.app.toggle_axis = False + # Open Preferences Window + if key == QtCore.Qt.Key_P: + self.app.on_preferences() + return + # Rotate Object by 90 degree CCW if key == QtCore.Qt.Key_R: self.app.on_rotate(silent=True, preset=-90) return + # Toggle Workspace + if key == QtCore.Qt.Key_W: + self.app.on_workspace_menu() + return + + # Skew on X axis + if key == QtCore.Qt.Key_X: + self.app.on_skewx() + return + + # Skew on Y axis + if key == QtCore.Qt.Key_Y: + self.app.on_skewy() + return + elif modifiers == QtCore.Qt.AltModifier: + # 2-Sided PCB Tool + if key == QtCore.Qt.Key_D: + self.app.dblsidedtool.run() + return + + # Non-Copper Clear Tool + if key == QtCore.Qt.Key_N: + self.app.ncclear_tool.run() + return + + # Transformation Tool + if key == QtCore.Qt.Key_R: + self.app.measurement_tool.run() + return + + # Cutout Tool + if key == QtCore.Qt.Key_U: + self.app.cutout_tool.run() + return + else: # Zoom Fit if key == QtCore.Qt.Key_1: @@ -316,10 +364,6 @@ class ObjectCollection(QtCore.QAbstractItemModel): select.ui.plot_cb.toggle() self.app.delete_selection_shape() - # Copy Object Name - if key == QtCore.Qt.Key_C: - self.app.on_copy_name() - # Copy Object Name if key == QtCore.Qt.Key_E: self.app.object2editor() @@ -340,12 +384,22 @@ class ObjectCollection(QtCore.QAbstractItemModel): if key == QtCore.Qt.Key_N: self.app.on_new_geometry() + # Set Origin + if key == QtCore.Qt.Key_O: + self.app.on_set_origin() + return + + # Set Origin + if key == QtCore.Qt.Key_P: + self.app.properties_tool.run() + return + # Change Units if key == QtCore.Qt.Key_Q: if self.app.options["units"] == 'MM': - self.app.general_options_form.general_group.units_radio.set_value("IN") + self.app.general_options_form.general_app_group.units_radio.set_value("IN") else: - self.app.general_options_form.general_group.units_radio.set_value("MM") + self.app.general_options_form.general_app_group.units_radio.set_value("MM") self.app.on_toggle_units() # Rotate Object by 90 degree CW diff --git a/PlotCanvas.py b/PlotCanvas.py index ee7ebb7d..56333568 100644 --- a/PlotCanvas.py +++ b/PlotCanvas.py @@ -65,7 +65,7 @@ class PlotCanvas(QtCore.QObject): self.draw_workspace() # if self.app.defaults['global_workspace'] is True: - # if self.app.general_options_form.general_group.units_radio.get_value().upper() == 'MM': + # if self.app.general_options_form.general_app_group.units_radio.get_value().upper() == 'MM': # self.wkspace_t = Line(pos=) self.shape_collections = [] @@ -92,7 +92,7 @@ class PlotCanvas(QtCore.QObject): a3p_mm = np.array([(0, 0), (297, 0), (297, 420), (0, 420)]) a3l_mm = np.array([(0, 0), (420, 0), (420, 297), (0, 297)]) - if self.app.general_options_form.general_group.units_radio.get_value().upper() == 'MM': + if self.app.general_options_form.general_app_group.units_radio.get_value().upper() == 'MM': if self.app.defaults['global_workspaceT'] == 'A4P': a = a4p_mm elif self.app.defaults['global_workspaceT'] == 'A4L': diff --git a/README.md b/README.md index 1e9d5413..9b2e2bb4 100644 --- a/README.md +++ b/README.md @@ -9,6 +9,13 @@ CAD program, and create G-Code for Isolation routing. ================================================= +27.01.2018 + +- added more key shortcuts into the application; they are now displayed in the GUI menu's +- reorganized the Edit -> Preferences -> Global +- redesigned the messagebox that is showed when quiting ot creating a New Project: now it has an option ('Cancel') to abort the process returning to the app + + 26.01.2019 - fixed grbl_11 postprocessor in linear_code() function diff --git a/flatcamTools/ToolCalculators.py b/flatcamTools/ToolCalculators.py index d02d765f..dc499972 100644 --- a/flatcamTools/ToolCalculators.py +++ b/flatcamTools/ToolCalculators.py @@ -141,6 +141,9 @@ class ToolCalculator(FlatCAMTool): FlatCAMTool.run(self) self.app.ui.notebook.setTabText(2, "Calc. Tool") + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='ALT+C', **kwargs) + def on_calculate_tool_dia(self): # Calculation: # Manufacturer gives total angle of the the tip but we need only half of it diff --git a/flatcamTools/ToolCutout.py b/flatcamTools/ToolCutout.py index d11f6044..c7825b62 100644 --- a/flatcamTools/ToolCutout.py +++ b/flatcamTools/ToolCutout.py @@ -9,7 +9,7 @@ from FlatCAMObj import FlatCAMGeometry, FlatCAMExcellon, FlatCAMGerber class ToolCutout(FlatCAMTool): - toolName = "Cutout PCB Tool" + toolName = "Cutout PCB" def __init__(self, app): FlatCAMTool.__init__(self, app) @@ -188,6 +188,9 @@ class ToolCutout(FlatCAMTool): FlatCAMTool.run(self) self.app.ui.notebook.setTabText(2, "Cutout Tool") + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='ALT+U', **kwargs) + def on_freeform_cutout(self): def subtract_rectangle(obj_, x0, y0, x1, y1): diff --git a/flatcamTools/ToolDblSided.py b/flatcamTools/ToolDblSided.py index fc2bc5ec..783b14a1 100644 --- a/flatcamTools/ToolDblSided.py +++ b/flatcamTools/ToolDblSided.py @@ -8,7 +8,7 @@ from PyQt5 import QtCore class DblSidedTool(FlatCAMTool): - toolName = "Double-Sided PCB Tool" + toolName = "2-Sided PCB" def __init__(self, app): FlatCAMTool.__init__(self, app) @@ -254,6 +254,9 @@ class DblSidedTool(FlatCAMTool): self.axis_location.set_value('point') self.drill_dia.set_value(1) + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='ALT+D', **kwargs) + def on_combo_box_type(self): obj_type = self.box_combo_type.currentIndex() self.box_combo.setRootModelIndex(self.app.collection.index(obj_type, 0, QtCore.QModelIndex())) diff --git a/flatcamTools/ToolFilm.py b/flatcamTools/ToolFilm.py index 8d8060c6..94638ada 100644 --- a/flatcamTools/ToolFilm.py +++ b/flatcamTools/ToolFilm.py @@ -6,7 +6,7 @@ from PyQt5 import QtGui, QtCore, QtWidgets class Film(FlatCAMTool): - toolName = "Film PCB Tool" + toolName = "Film PCB" def __init__(self, app): FlatCAMTool.__init__(self, app) @@ -154,6 +154,9 @@ class Film(FlatCAMTool): FlatCAMTool.run(self) self.app.ui.notebook.setTabText(2, "Film Tool") + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='ALT+L', **kwargs) + def on_film_creation(self): try: name = self.tf_object_combo.currentText() diff --git a/flatcamTools/ToolMeasurement.py b/flatcamTools/ToolMeasurement.py index d7ed0637..b786ad88 100644 --- a/flatcamTools/ToolMeasurement.py +++ b/flatcamTools/ToolMeasurement.py @@ -7,12 +7,12 @@ from math import sqrt class Measurement(FlatCAMTool): - toolName = "Measurement Tool" + toolName = "Measurement" def __init__(self, app): FlatCAMTool.__init__(self, app) - self.units = self.app.general_options_form.general_group.units_radio.get_value().lower() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().lower() ## Title title_label = QtWidgets.QLabel("%s
" % self.toolName) @@ -165,10 +165,13 @@ class Measurement(FlatCAMTool): # Switch notebook to tool page self.app.ui.notebook.setCurrentWidget(self.app.ui.tool_tab) - self.units = self.app.general_options_form.general_group.units_radio.get_value().lower() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().lower() self.show() self.app.ui.notebook.setTabText(2, "Meas. Tool") + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='CTRL+M', **kwargs) + def on_key_release_meas(self, event): if event.key == 'escape': # abort the measurement action @@ -217,7 +220,7 @@ class Measurement(FlatCAMTool): else: # ENABLE the Measuring TOOL self.active = True - self.units = self.app.general_options_form.general_group.units_radio.get_value().lower() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().lower() # we disconnect the mouse/key handlers from wherever the measurement tool was called if self.app.call_source == 'app': diff --git a/flatcamTools/ToolMove.py b/flatcamTools/ToolMove.py index 84dc7b19..b7fd1e2e 100644 --- a/flatcamTools/ToolMove.py +++ b/flatcamTools/ToolMove.py @@ -31,7 +31,7 @@ class ToolMove(FlatCAMTool): self.sel_shapes = ShapeCollection(parent=self.app.plotcanvas.vispy_canvas.view.scene, layers=1) def install(self, icon=None, separator=None, **kwargs): - FlatCAMTool.install(self, icon, separator, **kwargs) + FlatCAMTool.install(self, icon, separator, shortcut='M', **kwargs) def run(self): if self.app.tool_tab_locked is True: diff --git a/flatcamTools/ToolNonCopperClear.py b/flatcamTools/ToolNonCopperClear.py index 40ff011d..4782a7bd 100644 --- a/flatcamTools/ToolNonCopperClear.py +++ b/flatcamTools/ToolNonCopperClear.py @@ -7,7 +7,7 @@ import time class NonCopperClear(FlatCAMTool, Gerber): - toolName = "Non-Copper Clearing Tool" + toolName = "Non-Copper Clearing" def __init__(self, app): self.app = app @@ -234,7 +234,7 @@ class NonCopperClear(FlatCAMTool, Gerber): self.generate_ncc_button.clicked.connect(self.on_ncc) def install(self, icon=None, separator=None, **kwargs): - FlatCAMTool.install(self, icon, separator, **kwargs) + FlatCAMTool.install(self, icon, separator, shortcut='ALT+N', **kwargs) def run(self): FlatCAMTool.run(self) @@ -322,13 +322,13 @@ class NonCopperClear(FlatCAMTool, Gerber): self.obj_name = "" self.ncc_obj = None self.tool_type_item_options = ["C1", "C2", "C3", "C4", "B", "V"] - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() def build_ui(self): self.ui_disconnect() # updated units - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() if self.units == "IN": self.addtool_entry.set_value(0.039) diff --git a/flatcamTools/ToolPaint.py b/flatcamTools/ToolPaint.py index 16928970..2a14645f 100644 --- a/flatcamTools/ToolPaint.py +++ b/flatcamTools/ToolPaint.py @@ -5,7 +5,7 @@ from ObjectCollection import * class ToolPaint(FlatCAMTool, Gerber): - toolName = "Paint Area Tool" + toolName = "Paint Area" def __init__(self, app): self.app = app @@ -290,7 +290,7 @@ class ToolPaint(FlatCAMTool, Gerber): def install(self, icon=None, separator=None, **kwargs): - FlatCAMTool.install(self, icon, separator, **kwargs) + FlatCAMTool.install(self, icon, separator, shortcut='ALT+P', **kwargs) def run(self): FlatCAMTool.run(self) @@ -327,7 +327,7 @@ class ToolPaint(FlatCAMTool, Gerber): self.paintoverlap_entry.set_value(self.default_data["paintoverlap"]) # updated units - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() if self.units == "IN": self.addtool_entry.set_value(0.039) @@ -390,7 +390,7 @@ class ToolPaint(FlatCAMTool, Gerber): pass # updated units - self.units = self.app.general_options_form.general_group.units_radio.get_value().upper() + self.units = self.app.general_options_form.general_app_group.units_radio.get_value().upper() sorted_tools = [] for k, v in self.paint_tools.items(): diff --git a/flatcamTools/ToolPanelize.py b/flatcamTools/ToolPanelize.py index 905f9293..cdad3943 100644 --- a/flatcamTools/ToolPanelize.py +++ b/flatcamTools/ToolPanelize.py @@ -6,7 +6,7 @@ import time class Panelize(FlatCAMTool): - toolName = "Panelize PCB Tool" + toolName = "Panelize PCB" def __init__(self, app): super(Panelize, self).__init__(self) @@ -197,6 +197,9 @@ class Panelize(FlatCAMTool): FlatCAMTool.run(self) self.app.ui.notebook.setTabText(2, "Panel. Tool") + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='ALT+Z', **kwargs) + def on_panelize(self): name = self.object_combo.currentText() diff --git a/flatcamTools/ToolProperties.py b/flatcamTools/ToolProperties.py index b2f2eb52..06222f8a 100644 --- a/flatcamTools/ToolProperties.py +++ b/flatcamTools/ToolProperties.py @@ -53,6 +53,9 @@ class Properties(FlatCAMTool): FlatCAMTool.run(self) self.properties() + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='P', **kwargs) + def properties(self): obj_list = self.app.collection.get_selected() if not obj_list: @@ -86,10 +89,10 @@ class Properties(FlatCAMTool): width = abs(ymax - ymin) self.addChild(dims, ['Length:', '%.4f %s' % ( - length, self.app.general_options_form.general_group.units_radio.get_value().lower())], True) + length, self.app.general_options_form.general_app_group.units_radio.get_value().lower())], True) self.addChild(dims, ['Width:', '%.4f %s' % ( - width, self.app.general_options_form.general_group.units_radio.get_value().lower())], True) - if self.app.general_options_form.general_group.units_radio.get_value().lower() == 'mm': + width, self.app.general_options_form.general_app_group.units_radio.get_value().lower())], True) + if self.app.general_options_form.general_app_group.units_radio.get_value().lower() == 'mm': area = (length * width) / 100 self.addChild(dims, ['Box Area:', '%.4f %s' % (area, 'cm2')], True) else: diff --git a/flatcamTools/ToolTransform.py b/flatcamTools/ToolTransform.py index 45b603bc..7d641494 100644 --- a/flatcamTools/ToolTransform.py +++ b/flatcamTools/ToolTransform.py @@ -370,6 +370,9 @@ class ToolTransform(FlatCAMTool): FlatCAMTool.run(self) self.app.ui.notebook.setTabText(2, "Transform Tool") + def install(self, icon=None, separator=None, **kwargs): + FlatCAMTool.install(self, icon, separator, shortcut='ALT+R', **kwargs) + def on_rotate(self): try: value = float(self.rotate_entry.get_value()) diff --git a/share/toggle_units16.png b/share/toggle_units16.png new file mode 100644 index 00000000..164b823f Binary files /dev/null and b/share/toggle_units16.png differ diff --git a/share/toggle_units32.png b/share/toggle_units32.png new file mode 100644 index 00000000..7e58fdfb Binary files /dev/null and b/share/toggle_units32.png differ