Project Make Support: implemented the MakePropertiesDialog class and extended the Project class accordingly. make_support

Sat, 14 Apr 2018 18:48:38 +0200

author
Detlev Offenbach <detlev@die-offenbachs.de>
date
Sat, 14 Apr 2018 18:48:38 +0200
branch
make_support
changeset 6248
9458a3d45f27
parent 6245
6499ccd42dd6
child 6251
02afc7d22c41

Project Make Support: implemented the MakePropertiesDialog class and extended the Project class accordingly.

Project/MakePropertiesDialog.py file | annotate | diff | comparison | revisions
Project/MakePropertiesDialog.ui file | annotate | diff | comparison | revisions
Project/Project.py file | annotate | diff | comparison | revisions
Project/PropertiesDialog.py file | annotate | diff | comparison | revisions
eric6.e4p file | annotate | diff | comparison | revisions
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Project/MakePropertiesDialog.py	Sat Apr 14 18:48:38 2018 +0200
@@ -0,0 +1,88 @@
+# -*- coding: utf-8 -*-
+
+# Copyright (c) 2018 Detlev Offenbach <detlev@die-offenbachs.de>
+#
+
+"""
+Module implementing a dialog to enter the properties for 'make'.
+"""
+
+from __future__ import unicode_literals
+
+from PyQt5.QtWidgets import QDialog
+
+from E5Gui.E5PathPicker import E5PathPickerModes
+
+from .Ui_MakePropertiesDialog import Ui_MakePropertiesDialog
+
+
+class MakePropertiesDialog(QDialog, Ui_MakePropertiesDialog):
+    """
+    Class implementing a dialog to enter the properties for 'make'.
+    """
+    def __init__(self, project, new, parent=None):
+        """
+        Constructor
+        
+        @param project reference to the project object
+        @type Project
+        @param new flag indicating the generation of a new project
+        @type bool
+        @param parent reference to the parent widget of this dialog
+        @type QWidget
+        """
+        super(MakePropertiesDialog, self).__init__(parent)
+        self.setupUi(self)
+        
+        self.__project = project
+        
+        self.makePicker.setMode(E5PathPickerModes.OpenFileMode)
+        self.makePicker.setFilters(self.tr("All Files (*)"))
+        
+        self.makefilePicker.setMode(E5PathPickerModes.OpenFileMode)
+        self.makefilePicker.setDefaultDirectory(self.__project.ppath)
+        self.makefilePicker.setFilters(self.tr(
+            "Makefiles (*makefile Makefile *.mak);;All Files (*)"))
+        
+        self.initDialog()
+        
+        msh = self.minimumSizeHint()
+        self.resize(max(self.width(), msh.width()), msh.height())
+    
+    def initDialog(self):
+        """
+        Public method to initialize the dialog's data.
+        """
+        makeData = self.__project.pdata["MAKEPARAMS"]
+        
+        if makeData["MakeExecutable"]:
+            self.makePicker.setText(makeData["MakeExecutable"])
+        else:
+            self.makePicker.setText(self.__project.DefaultMake)
+        if makeData["MakeFile"]:
+            self.makefilePicker.setText(makeData["MakeFile"])
+        else:
+            self.makefilePicker.setText(self.__project.DefaultMakefile)
+        self.makeTargetEdit.setText(makeData["MakeTarget"])
+        self.makeParametersEdit.setText(makeData["MakeParameters"])
+        self.testOnlyCheckBox.setChecked(makeData["MakeTestOnly"])
+    
+    def storeData(self):
+        """
+        Public method to store the entered/modified data.
+        """
+        makeData = self.__project.pdata["MAKEPARAMS"]
+        
+        makeExe = self.makePicker.text()
+        if makeExe == self.__project.DefaultMake:
+            makeExe = ""
+        makeData["MakeExecutable"] = makeExe
+        
+        makefile = self.__project.getRelativePath(self.makefilePicker.text())
+        if makefile == self.__project.DefaultMakefile:
+            makefile = ""
+        makeData["MakeFile"] = makefile
+        
+        makeData["MakeTarget"] = self.makeTargetEdit.text()
+        makeData["MakeParameters"] = self.makeParametersEdit.text()
+        makeData["MakeTestOnly"] = self.testOnlyCheckBox.isChecked()
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Project/MakePropertiesDialog.ui	Sat Apr 14 18:48:38 2018 +0200
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>MakePropertiesDialog</class>
+ <widget class="QDialog" name="MakePropertiesDialog">
+  <property name="geometry">
+   <rect>
+    <x>0</x>
+    <y>0</y>
+    <width>600</width>
+    <height>266</height>
+   </rect>
+  </property>
+  <property name="windowTitle">
+   <string>Make Properties</string>
+  </property>
+  <property name="sizeGripEnabled">
+   <bool>true</bool>
+  </property>
+  <layout class="QVBoxLayout" name="verticalLayout">
+   <item>
+    <widget class="QLabel" name="label">
+     <property name="text">
+      <string>'make' Executable (leave empty to use global 'make'):</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="E5PathPicker" name="makePicker" native="true">
+     <property name="sizePolicy">
+      <sizepolicy hsizetype="Expanding" vsizetype="Preferred">
+       <horstretch>0</horstretch>
+       <verstretch>0</verstretch>
+      </sizepolicy>
+     </property>
+     <property name="focusPolicy">
+      <enum>Qt::StrongFocus</enum>
+     </property>
+     <property name="toolTip">
+      <string>Enter the executable name of the make utility</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="QLabel" name="label_2">
+     <property name="text">
+      <string>'makefile' path or directory (without file name 'makefile' will be used):</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="E5PathPicker" name="makefilePicker" native="true">
+     <property name="sizePolicy">
+      <sizepolicy hsizetype="Expanding" vsizetype="Preferred">
+       <horstretch>0</horstretch>
+       <verstretch>0</verstretch>
+      </sizepolicy>
+     </property>
+     <property name="focusPolicy">
+      <enum>Qt::StrongFocus</enum>
+     </property>
+     <property name="toolTip">
+      <string>Enter the name and/or path of the makefile</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="QLabel" name="label_3">
+     <property name="text">
+      <string>Make Target:</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="E5ClearableLineEdit" name="makeTargetEdit">
+     <property name="toolTip">
+      <string>Enter the make target to be built</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="QLabel" name="label_4">
+     <property name="text">
+      <string>Make Command Parameters (enclose parameters containing spaces in &quot;&quot;):</string>
+     </property>
+     <property name="wordWrap">
+      <bool>true</bool>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="E5ClearableLineEdit" name="makeParametersEdit">
+     <property name="toolTip">
+      <string>Enter the command parameters for make</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="QCheckBox" name="testOnlyCheckBox">
+     <property name="toolTip">
+      <string>Select to just test for changes needing a make run</string>
+     </property>
+     <property name="text">
+      <string>Test for changes only when run automatically</string>
+     </property>
+    </widget>
+   </item>
+   <item>
+    <widget class="QDialogButtonBox" name="buttonBox">
+     <property name="orientation">
+      <enum>Qt::Horizontal</enum>
+     </property>
+     <property name="standardButtons">
+      <set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set>
+     </property>
+    </widget>
+   </item>
+  </layout>
+ </widget>
+ <customwidgets>
+  <customwidget>
+   <class>E5PathPicker</class>
+   <extends>QWidget</extends>
+   <header>E5Gui/E5PathPicker.h</header>
+   <container>1</container>
+  </customwidget>
+  <customwidget>
+   <class>E5ClearableLineEdit</class>
+   <extends>QLineEdit</extends>
+   <header>E5Gui/E5LineEdit.h</header>
+  </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections>
+  <connection>
+   <sender>buttonBox</sender>
+   <signal>accepted()</signal>
+   <receiver>MakePropertiesDialog</receiver>
+   <slot>accept()</slot>
+   <hints>
+    <hint type="sourcelabel">
+     <x>248</x>
+     <y>254</y>
+    </hint>
+    <hint type="destinationlabel">
+     <x>157</x>
+     <y>274</y>
+    </hint>
+   </hints>
+  </connection>
+  <connection>
+   <sender>buttonBox</sender>
+   <signal>rejected()</signal>
+   <receiver>MakePropertiesDialog</receiver>
+   <slot>reject()</slot>
+   <hints>
+    <hint type="sourcelabel">
+     <x>316</x>
+     <y>260</y>
+    </hint>
+    <hint type="destinationlabel">
+     <x>286</x>
+     <y>274</y>
+    </hint>
+   </hints>
+  </connection>
+ </connections>
+</ui>
--- a/Project/Project.py	Fri Apr 13 19:57:02 2018 +0200
+++ b/Project/Project.py	Sat Apr 14 18:48:38 2018 +0200
@@ -148,6 +148,9 @@
     
     eols = [os.linesep, "\n", "\r", "\r\n"]
     
+    DefaultMake = "make"
+    DefaultMakefile = "makefile"
+    
     def __init__(self, parent=None, filename=None):
         """
         Constructor
@@ -431,7 +434,6 @@
         self.dbgTracePython = False
         self.dbgAutoContinue = True
         
-        # TODO: add 'make' support
         self.pdata = {
             "DESCRIPTION": "",
             "VERSION": "",
@@ -466,6 +468,14 @@
             "PACKAGERSPARMS": {},
             "DOCUMENTATIONPARMS": {},
             "OTHERTOOLSPARMS": {},
+            "MAKEPARAMS": {
+                "MakeEnabled": False,
+                "MakeExecutable": "",
+                "MakeFile": "",
+                "MakeTarget": "",
+                "MakeParameters": "",
+                "MakeTestOnly": True,
+            },
             "EOL": -1,
         }
         
@@ -2254,6 +2264,7 @@
                         .format(self.ppath))
                     self.vcs = self.initVCS()
                     return
+                
                 # create an empty __init__.py file to make it a Python package
                 # (only for Python and Python3)
                 if self.pdata["PROGLANGUAGE"] in \
@@ -2262,6 +2273,7 @@
                     f = open(fn, "w", encoding="utf-8")
                     f.close()
                     self.appendFile(fn, True)
+                
                 # create an empty main script file, if a name was given
                 if self.pdata["MAINSCRIPT"]:
                     if not os.path.isabs(self.pdata["MAINSCRIPT"]):
@@ -2272,6 +2284,18 @@
                     f = open(ms, "w")
                     f.close()
                     self.appendFile(ms, True)
+                
+                if self.pdata["MAKEPARAMS"]["MakeEnabled"]:
+                    mf = self.pdata["MAKEPARAMS"]["MakeFile"]
+                    if mf:
+                        if not os.path.isabs(mf):
+                            mf = os.path.join(self.ppath, mf)
+                    else:
+                        mf = os.path.join(self.ppath, Project.DefaultMakefile)
+                    f = open(mf, "w")
+                    f.close()
+                    self.appendFile(mf)
+                
                 tpd = os.path.join(self.ppath, self.translationsRoot)
                 if not self.translationsRoot.endswith(os.sep):
                     tpd = os.path.dirname(tpd)
@@ -2318,11 +2342,32 @@
                                 self.tr(
                                     "<p>The mainscript <b>{0}</b> could not"
                                     " be created.<br/>Reason: {1}</p>")
-                                .format(self.ppath, str(err)))
-                    self.appendFile(ms)
+                                .format(ms, str(err)))
+                    self.appendFile(ms, True)
                 else:
                     ms = ""
                 
+                if self.pdata["MAKEPARAMS"]["MakeEnabled"]:
+                    mf = self.pdata["MAKEPARAMS"]["MakeFile"]
+                    if mf:
+                        if not os.path.isabs(mf):
+                            mf = os.path.join(self.ppath, mf)
+                    else:
+                        mf = os.path.join(self.ppath, Project.DefaultMakefile)
+                    if not os.path.exists(mf):
+                        try:
+                            f = open(mf, "w")
+                            f.close()
+                        except EnvironmentError as err:
+                            E5MessageBox.critical(
+                                self.ui,
+                                self.tr("Create Makefile"),
+                                self.tr(
+                                    "<p>The makefile <b>{0}</b> could not"
+                                    " be created.<br/>Reason: {1}</p>")
+                                .format(mf, str(err)))
+                    self.appendFile(mf)
+                
                 # add existing files to the project
                 res = E5MessageBox.yesNo(
                     self.ui,
@@ -2580,6 +2625,27 @@
                 if os.path.exists(ms):
                     self.appendFile(ms)
             
+            if self.pdata["MAKEPARAMS"]["MakeEnabled"]:
+                mf = self.pdata["MAKEPARAMS"]["MakeFile"]
+                if mf:
+                    if not os.path.isabs(mf):
+                        mf = os.path.join(self.ppath, mf)
+                else:
+                    mf = os.path.join(self.ppath, Project.DefaultMakefile)
+                if not os.path.exists(mf):
+                    try:
+                        f = open(mf, "w")
+                        f.close()
+                    except EnvironmentError as err:
+                        E5MessageBox.critical(
+                            self.ui,
+                            self.tr("Create Makefile"),
+                            self.tr(
+                                "<p>The makefile <b>{0}</b> could not"
+                                " be created.<br/>Reason: {1}</p>")
+                            .format(mf, str(err)))
+                self.appendFile(mf)
+            
             if self.pdata["PROJECTTYPE"] != projectType:
                 # reinitialize filetype associations
                 self.initFileTypes()
--- a/Project/PropertiesDialog.py	Fri Apr 13 19:57:02 2018 +0200
+++ b/Project/PropertiesDialog.py	Sat Apr 14 18:48:38 2018 +0200
@@ -116,6 +116,8 @@
                     self.tr("The project is not version controlled."))
                 self.vcsInfoButton.hide()
             self.vcsCheckBox.hide()
+            self.makeCheckBox.setChecked(
+                self.project.pdata["MAKEPARAMS"]["MakeEnabled"])
         else:
             self.languageComboBox.setCurrentIndex(
                 self.languageComboBox.findText("Python3"))
@@ -199,7 +201,6 @@
         Private slot to display the make properties dialog.
         """
         if self.makePropertiesDlg is None:
-            # TODO: add 'make' support - implement MakePropertiesDialog
             from .MakePropertiesDialog import MakePropertiesDialog
             self.makePropertiesDlg = \
                 MakePropertiesDialog(self.project, self.newProject, self)
@@ -304,5 +305,7 @@
         if self.transPropertiesDlg is not None:
             self.transPropertiesDlg.storeData()
         
+        self.project.pdata["MAKEPARAMS"]["MakeEnabled"] = \
+            self.makeCheckBox.isChecked()
         if self.makePropertiesDlg is not None:
             self.makePropertiesDlg.storeData()
--- a/eric6.e4p	Fri Apr 13 19:57:02 2018 +0200
+++ b/eric6.e4p	Sat Apr 14 18:48:38 2018 +0200
@@ -917,6 +917,7 @@
     <Source>Project/DebuggerPropertiesDialog.py</Source>
     <Source>Project/FiletypeAssociationDialog.py</Source>
     <Source>Project/LexerAssociationDialog.py</Source>
+    <Source>Project/MakePropertiesDialog.py</Source>
     <Source>Project/NewDialogClassDialog.py</Source>
     <Source>Project/NewPythonPackageDialog.py</Source>
     <Source>Project/Project.py</Source>
@@ -2058,6 +2059,7 @@
     <Form>Project/DebuggerPropertiesDialog.ui</Form>
     <Form>Project/FiletypeAssociationDialog.ui</Form>
     <Form>Project/LexerAssociationDialog.ui</Form>
+    <Form>Project/MakePropertiesDialog.ui</Form>
     <Form>Project/NewDialogClassDialog.ui</Form>
     <Form>Project/NewPythonPackageDialog.ui</Form>
     <Form>Project/PropertiesDialog.ui</Form>

eric ide

mercurial