src/eric7/Project/PropertiesDialog.py

branch
eric7-maintenance
changeset 9264
18a7312cfdb3
parent 9197
301be1e80ad6
parent 9221
bf71ee032bb4
child 9371
1da8bc75946f
equal deleted inserted replaced
9241:d23e9854aea4 9264:18a7312cfdb3
1 # -*- coding: utf-8 -*-
2
3 # Copyright (c) 2002 - 2022 Detlev Offenbach <detlev@die-offenbachs.de>
4 #
5
6 """
7 Module implementing the project properties dialog.
8 """
9
10 import contextlib
11 import os
12
13 import trove_classifiers
14
15 from PyQt6.QtCore import QDir, pyqtSlot
16 from PyQt6.QtWidgets import QDialog, QDialogButtonBox
17
18 from EricWidgets.EricApplication import ericApp
19 from EricWidgets.EricPathPicker import EricPathPickerModes
20
21 from .Ui_PropertiesDialog import Ui_PropertiesDialog
22
23 from QScintilla.DocstringGenerator import getSupportedDocstringTypes
24
25 from Testing.Interfaces import FrameworkNames
26
27 import Utilities
28 import Preferences
29 import UI.PixmapCache
30
31
32 class PropertiesDialog(QDialog, Ui_PropertiesDialog):
33 """
34 Class implementing the project properties dialog.
35 """
36
37 def __init__(self, project, new=True, parent=None, name=None):
38 """
39 Constructor
40
41 @param project reference to the project object
42 @param new flag indicating the generation of a new project
43 @param parent parent widget of this dialog (QWidget)
44 @param name name of this dialog (string)
45 """
46 super().__init__(parent)
47 if name:
48 self.setObjectName(name)
49 self.setupUi(self)
50
51 self.dirPicker.setMode(EricPathPickerModes.DIRECTORY_MODE)
52 self.mainscriptPicker.setMode(EricPathPickerModes.OPEN_FILE_MODE)
53
54 self.makeButton.setIcon(UI.PixmapCache.getIcon("makefile"))
55
56 self.docstringStyleComboBox.addItem(self.tr("None"), "")
57 for docstringType, docstringStyle in sorted(getSupportedDocstringTypes()):
58 self.docstringStyleComboBox.addItem(docstringStyle, docstringType)
59
60 self.project = project
61 self.newProject = new
62 self.transPropertiesDlg = None
63 self.spellPropertiesDlg = None
64 self.makePropertiesDlg = None
65
66 patterns = []
67 for pattern, filetype in self.project.pdata["FILETYPES"].items():
68 if filetype == "SOURCES":
69 patterns.append(pattern)
70 filters = self.tr("Source Files ({0});;All Files (*)").format(
71 " ".join(sorted(patterns))
72 )
73 self.mainscriptPicker.setFilters(filters)
74
75 self.languageComboBox.addItems(project.getProgrammingLanguages())
76
77 projectTypes = []
78 for projectTypeItem in project.getProjectTypes().items():
79 projectTypes.append((projectTypeItem[1], projectTypeItem[0]))
80 self.projectTypeComboBox.clear()
81 for projectType in sorted(projectTypes):
82 self.projectTypeComboBox.addItem(projectType[0], projectType[1])
83
84 ipath = Preferences.getMultiProject("Workspace") or Utilities.getHomeDir()
85 self.__initPaths = [
86 Utilities.fromNativeSeparators(ipath),
87 Utilities.fromNativeSeparators(ipath) + "/",
88 ]
89
90 self.licenseComboBox.lineEdit().setClearButtonEnabled(True)
91 self.__populateLicenseComboBox()
92
93 if not new:
94 name = os.path.splitext(self.project.pfile)[0]
95 self.nameEdit.setText(os.path.basename(name))
96 self.languageComboBox.setCurrentIndex(
97 self.languageComboBox.findText(self.project.pdata["PROGLANGUAGE"])
98 )
99 self.mixedLanguageCheckBox.setChecked(self.project.pdata["MIXEDLANGUAGE"])
100 curIndex = self.projectTypeComboBox.findData(
101 self.project.pdata["PROJECTTYPE"]
102 )
103 if curIndex == -1:
104 curIndex = self.projectTypeComboBox.findData("PyQt6")
105 self.projectTypeComboBox.setCurrentIndex(curIndex)
106 self.dirPicker.setText(self.project.ppath)
107 self.versionEdit.setText(self.project.pdata["VERSION"])
108 self.mainscriptPicker.setText(self.project.pdata["MAINSCRIPT"])
109 self.authorEdit.setText(self.project.pdata["AUTHOR"])
110 self.emailEdit.setText(self.project.pdata["EMAIL"])
111 self.descriptionEdit.setPlainText(self.project.pdata["DESCRIPTION"])
112 self.eolComboBox.setCurrentIndex(self.project.pdata["EOL"])
113 self.vcsLabel.show()
114 if self.project.vcs is not None:
115 vcsSystemsDict = (
116 ericApp()
117 .getObject("PluginManager")
118 .getPluginDisplayStrings("version_control")
119 )
120 try:
121 vcsSystemDisplay = vcsSystemsDict[self.project.pdata["VCS"]]
122 except KeyError:
123 vcsSystemDisplay = "None"
124 self.vcsLabel.setText(
125 self.tr("The project is version controlled by <b>{0}</b>.").format(
126 vcsSystemDisplay
127 )
128 )
129 self.vcsInfoButton.show()
130 else:
131 self.vcsLabel.setText(self.tr("The project is not version controlled."))
132 self.vcsInfoButton.hide()
133 self.vcsCheckBox.hide()
134 self.makeCheckBox.setChecked(
135 self.project.pdata["MAKEPARAMS"]["MakeEnabled"]
136 )
137 cindex = self.docstringStyleComboBox.findData(
138 self.project.pdata["DOCSTRING"]
139 )
140 self.docstringStyleComboBox.setCurrentIndex(cindex)
141 with contextlib.suppress(KeyError):
142 cindex = self.testingFrameworkComboBox.findData(
143 self.project.pdata["TESTING_FRAMEWORK"]
144 )
145 self.testingFrameworkComboBox.setCurrentIndex(cindex)
146 with contextlib.suppress(KeyError):
147 self.licenseComboBox.setCurrentText(self.project.pdata["LICENSE"])
148 else:
149 self.languageComboBox.setCurrentText("Python3")
150 self.projectTypeComboBox.setCurrentIndex(
151 self.projectTypeComboBox.findData("PyQt6")
152 )
153 self.dirPicker.setText(self.__initPaths[0])
154 self.versionEdit.setText("0.1")
155 self.vcsLabel.hide()
156 self.vcsInfoButton.hide()
157 if not self.project.vcsSoftwareAvailable():
158 self.vcsCheckBox.hide()
159
160 self.buttonBox.button(QDialogButtonBox.StandardButton.Ok).setEnabled(
161 bool(self.dirPicker.text())
162 and self.dirPicker.text() not in self.__initPaths
163 )
164
165 def __populateLicenseComboBox(self):
166 """
167 Private method to populate the license selector with the list of trove
168 license types.
169 """
170 self.licenseComboBox.addItem("")
171 self.licenseComboBox.addItems(
172 sorted(
173 classifier.split("::")[-1].strip()
174 for classifier in trove_classifiers.classifiers
175 if classifier.startswith("License ::")
176 )
177 )
178
179 @pyqtSlot(str)
180 def on_languageComboBox_currentTextChanged(self, language):
181 """
182 Private slot handling the selection of a programming language.
183
184 @param language text of the current item
185 @type str
186 """
187 curProjectType = self.getProjectType()
188
189 self.projectTypeComboBox.clear()
190 for projectType in sorted(
191 self.project.getProjectTypes(language).items(), key=lambda k: k[1]
192 ):
193 self.projectTypeComboBox.addItem(projectType[1], projectType[0])
194
195 index = self.projectTypeComboBox.findData(curProjectType)
196 if index == -1:
197 index = 0
198 self.projectTypeComboBox.setCurrentIndex(index)
199
200 curTestingFramework = self.testingFrameworkComboBox.currentText()
201 self.testingFrameworkComboBox.clear()
202 self.testingFrameworkComboBox.addItem(self.tr("None"), "")
203 with contextlib.suppress(KeyError):
204 for framework in sorted(FrameworkNames[language]):
205 self.testingFrameworkComboBox.addItem(framework, framework)
206 self.testingFrameworkComboBox.setCurrentText(curTestingFramework)
207
208 @pyqtSlot(str)
209 def on_dirPicker_textChanged(self, txt):
210 """
211 Private slot to handle a change of the project directory.
212
213 @param txt name of the project directory (string)
214 """
215 self.buttonBox.button(QDialogButtonBox.StandardButton.Ok).setEnabled(
216 bool(txt) and Utilities.fromNativeSeparators(txt) not in self.__initPaths
217 )
218
219 @pyqtSlot()
220 def on_spellPropertiesButton_clicked(self):
221 """
222 Private slot to display the spelling properties dialog.
223 """
224 if self.spellPropertiesDlg is None:
225 from .SpellingPropertiesDialog import SpellingPropertiesDialog
226
227 self.spellPropertiesDlg = SpellingPropertiesDialog(
228 self.project, self.newProject, self
229 )
230 res = self.spellPropertiesDlg.exec()
231 if res == QDialog.DialogCode.Rejected:
232 self.spellPropertiesDlg.initDialog() # reset the dialogs contents
233
234 @pyqtSlot()
235 def on_transPropertiesButton_clicked(self):
236 """
237 Private slot to display the translations properties dialog.
238 """
239 if self.transPropertiesDlg is None:
240 from .TranslationPropertiesDialog import TranslationPropertiesDialog
241
242 self.transPropertiesDlg = TranslationPropertiesDialog(
243 self.project, self.newProject, self
244 )
245 else:
246 self.transPropertiesDlg.initFilters()
247 res = self.transPropertiesDlg.exec()
248 if res == QDialog.DialogCode.Rejected:
249 self.transPropertiesDlg.initDialog() # reset the dialogs contents
250
251 @pyqtSlot()
252 def on_makeButton_clicked(self):
253 """
254 Private slot to display the make properties dialog.
255 """
256 if self.makePropertiesDlg is None:
257 from .MakePropertiesDialog import MakePropertiesDialog
258
259 self.makePropertiesDlg = MakePropertiesDialog(
260 self.project, self.newProject, self
261 )
262 res = self.makePropertiesDlg.exec()
263 if res == QDialog.DialogCode.Rejected:
264 self.makePropertiesDlg.initDialog()
265
266 @pyqtSlot(str)
267 def on_mainscriptPicker_pathSelected(self, script):
268 """
269 Private slot to check the selected main script name.
270
271 @param script name of the main script
272 @type str
273 """
274 if script:
275 ppath = self.dirPicker.text()
276 if ppath:
277 ppath = QDir(ppath).absolutePath() + QDir.separator()
278 script = script.replace(ppath, "")
279 self.mainscriptPicker.setText(script)
280
281 @pyqtSlot()
282 def on_mainscriptPicker_aboutToShowPathPickerDialog(self):
283 """
284 Private slot to perform actions before the main script selection dialog
285 is shown.
286 """
287 path = self.dirPicker.text()
288 if not path:
289 path = QDir.currentPath()
290 self.mainscriptPicker.setDefaultDirectory(path)
291
292 @pyqtSlot()
293 def on_vcsInfoButton_clicked(self):
294 """
295 Private slot to display a vcs information dialog.
296 """
297 if self.project.vcs is None:
298 return
299
300 from VCS.RepositoryInfoDialog import VcsRepositoryInfoDialog
301
302 info = self.project.vcs.vcsRepositoryInfos(self.project.ppath)
303 dlg = VcsRepositoryInfoDialog(self, info)
304 dlg.exec()
305
306 def getProjectType(self):
307 """
308 Public method to get the selected project type.
309
310 @return selected UI type (string)
311 """
312 return self.projectTypeComboBox.itemData(
313 self.projectTypeComboBox.currentIndex()
314 )
315
316 def getPPath(self):
317 """
318 Public method to get the project path.
319
320 @return data of the project directory edit (string)
321 """
322 return os.path.abspath(self.dirPicker.text())
323
324 def storeData(self):
325 """
326 Public method to store the entered/modified data.
327 """
328 self.project.ppath = os.path.abspath(self.dirPicker.text())
329 fn = self.nameEdit.text()
330 if fn:
331 self.project.name = fn
332 fn = "{0}.epj".format(fn)
333 self.project.pfile = os.path.join(self.project.ppath, fn)
334 else:
335 self.project.pfile = ""
336 self.project.pdata["VERSION"] = self.versionEdit.text()
337 fn = self.mainscriptPicker.text()
338 if fn:
339 fn = self.project.getRelativePath(fn)
340 self.project.pdata["MAINSCRIPT"] = fn
341 self.project.translationsRoot = os.path.splitext(fn)[0]
342 else:
343 self.project.pdata["MAINSCRIPT"] = ""
344 self.project.translationsRoot = ""
345 self.project.pdata["AUTHOR"] = self.authorEdit.text()
346 self.project.pdata["EMAIL"] = self.emailEdit.text()
347 self.project.pdata["DESCRIPTION"] = self.descriptionEdit.toPlainText()
348 self.project.pdata["PROGLANGUAGE"] = self.languageComboBox.currentText()
349 self.project.pdata["MIXEDLANGUAGE"] = self.mixedLanguageCheckBox.isChecked()
350 projectType = self.getProjectType()
351 if projectType is not None:
352 self.project.pdata["PROJECTTYPE"] = projectType
353 self.project.pdata["EOL"] = self.eolComboBox.currentIndex()
354
355 self.project.vcsRequested = self.vcsCheckBox.isChecked()
356
357 if self.spellPropertiesDlg is not None:
358 self.spellPropertiesDlg.storeData()
359
360 if self.transPropertiesDlg is not None:
361 self.transPropertiesDlg.storeData()
362
363 self.project.pdata["MAKEPARAMS"]["MakeEnabled"] = self.makeCheckBox.isChecked()
364 if self.makePropertiesDlg is not None:
365 self.makePropertiesDlg.storeData()
366
367 self.project.pdata["DOCSTRING"] = self.docstringStyleComboBox.currentData()
368
369 self.project.pdata[
370 "TESTING_FRAMEWORK"
371 ] = self.testingFrameworkComboBox.currentData()
372
373 self.project.pdata["LICENSE"] = self.licenseComboBox.currentText()

eric ide

mercurial