Skip to content

Commit

Permalink
Added local dir feedback when creating a new project
Browse files Browse the repository at this point in the history
  • Loading branch information
suricactus committed Sep 7, 2021
1 parent 7ad7fb4 commit 962dc2c
Show file tree
Hide file tree
Showing 4 changed files with 145 additions and 80 deletions.
54 changes: 47 additions & 7 deletions qfieldsync/gui/cloud_create_project_widget.py
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,11 @@
get_unique_empty_dirname,
)
from qfieldsync.libqfieldsync.utils.qgis import get_qgis_files_within_dir
from qfieldsync.utils.cloud_utils import to_cloud_title
from qfieldsync.utils.cloud_utils import (
LocalDirFeedback,
local_dir_feedback,
to_cloud_title,
)

WidgetUi, _ = loadUiType(
os.path.join(os.path.dirname(__file__), "../ui/cloud_create_project_widget.ui")
Expand All @@ -72,12 +76,13 @@ def __init__(
iface: QgisInterface,
network_manager: CloudNetworkAccessManager,
project: QgsProject,
parent: QWidget = None,
parent: QWidget,
) -> None:
"""Constructor."""
super(CloudCreateProjectWidget, self).__init__(parent=parent)
self.setupUi(self)

self.cloud_projects_dialog = parent
self.iface = iface
self.project = project
self.qfield_preferences = Preferences()
Expand All @@ -95,18 +100,18 @@ def __init__(
self.nextButton.clicked.connect(self.on_next_button_clicked)
self.backButton.clicked.connect(self.on_back_button_clicked)
self.createButton.clicked.connect(self.on_create_button_clicked)
self.dirnameButton.clicked.connect(self.on_dirname_button_clicked)
self.dirnameLineEdit.textChanged.connect(self.on_dirname_line_edit_text_changed)

self.use_current_project_directory_action = QAction(
QIcon(), self.tr("Use Current Project Directory")
)
self.use_current_project_directory_action.triggered.connect(
self.on_use_current_project_directory_action_triggered
)
self.dirnameToolButton.setMenu(QMenu())
self.dirnameToolButton.setPopupMode(QToolButton.MenuButtonPopup)
self.dirnameToolButton.menu().addAction(
self.use_current_project_directory_action
)
self.dirnameButton.setMenu(QMenu())
self.dirnameButton.setPopupMode(QToolButton.MenuButtonPopup)
self.dirnameButton.menu().addAction(self.use_current_project_directory_action)

self.projectNameLineEdit.setValidator(
QRegularExpressionValidator(
Expand Down Expand Up @@ -295,6 +300,30 @@ def get_unique_project_name(self, project: QgsProject) -> str:

return project_name

def set_dirname(self, dirname: str):
if self.cloudifyRadioButton.isChecked():
feedback, feedback_msg = local_dir_feedback(
dirname,
single_project_status=LocalDirFeedback.Error,
not_existing_status=LocalDirFeedback.Success,
)
elif self.createCloudRadioButton.isChecked():
feedback, feedback_msg = local_dir_feedback(dirname)
else:
raise NotImplementedError("Unknown create new button radio.")

self.dirnameFeedbackLabel.setText(feedback_msg)

if feedback == LocalDirFeedback.Error:
self.dirnameFeedbackLabel.setStyleSheet("color: red;")
self.createButton.setEnabled(False)
elif feedback == LocalDirFeedback.Warning:
self.dirnameFeedbackLabel.setStyleSheet("color: orange;")
self.createButton.setEnabled(True)
else:
self.dirnameFeedbackLabel.setStyleSheet("color: green;")
self.createButton.setEnabled(True)

def on_update_total_progressbar(self, current, layer_count, message):
self.convertProgressBar.setMaximum(layer_count)
self.convertProgressBar.setValue(current)
Expand Down Expand Up @@ -330,6 +359,7 @@ def on_next_button_clicked(self) -> None:
)
)
if self.cloudifyRadioButton.isChecked():
self.createButton.setEnabled(True)
self.dirnameLineEdit.setText(str(export_dirname))
elif self.createCloudRadioButton.isChecked():
self.dirnameLineEdit.setText(str(Path(self.project.fileName()).parent))
Expand All @@ -347,5 +377,15 @@ def on_create_button_clicked(self):
self.infoLabel.setText(self.createCloudInfoLabel.text())
self.create_empty_cloud_project()

def on_dirname_button_clicked(self):
dirname = self.cloud_projects_dialog.select_local_dir()

if dirname:
self.set_dirname(dirname)
self.dirnameLineEdit.setText(str(Path(dirname)))

def on_dirname_line_edit_text_changed(self, text: str):
self.set_dirname(self.dirnameLineEdit.text())

def on_use_current_project_directory_action_triggered(self):
self.dirnameLineEdit.setText(str(Path(self.project.fileName()).parent))
67 changes: 10 additions & 57 deletions qfieldsync/gui/cloud_projects_dialog.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,8 @@
* *
***************************************************************************/
"""
from enum import Enum
from pathlib import Path
from typing import Callable, Optional, Tuple
from typing import Callable, Optional

from qgis.core import QgsApplication, QgsProject
from qgis.PyQt.QtCore import (
Expand Down Expand Up @@ -68,8 +67,7 @@
from qfieldsync.gui.cloud_create_project_widget import CloudCreateProjectWidget
from qfieldsync.gui.cloud_login_dialog import CloudLoginDialog
from qfieldsync.gui.cloud_transfer_dialog import CloudTransferDialog
from qfieldsync.libqfieldsync.utils.qgis import get_qgis_files_within_dir
from qfieldsync.utils.cloud_utils import closure
from qfieldsync.utils.cloud_utils import LocalDirFeedback, closure, local_dir_feedback
from qfieldsync.utils.permissions import can_delete_project
from qfieldsync.utils.qt_utils import rounded_pixmap

Expand All @@ -78,12 +76,6 @@
)


class LocalDirFeedback(Enum):
Error = "error"
Warning = "warning"
Success = "success"


class CloudProjectsDialog(QDialog, CloudProjectsDialogUi):
projects_refreshed = pyqtSignal()
_current_cloud_project = None
Expand Down Expand Up @@ -517,19 +509,18 @@ def on_button_box_clicked(self) -> None:

def on_local_dir_line_edit_text_changed(self) -> None:
local_dir = self.localDirLineEdit.text()
self.submitButton.setEnabled(False)

feedback, feedback_msg = self.local_dir_feedback(local_dir)
feedback, feedback_msg = local_dir_feedback(local_dir)
self.localDirFeedbackLabel.setText(feedback_msg)

if feedback == LocalDirFeedback.Error:
self.localDirFeedbackLabel.setStyleSheet("color: red;")
self.submitButton.setEnabled(False)
elif feedback == LocalDirFeedback.Warning:
self.localDirFeedbackLabel.setStyleSheet("color: orange;")
self.submitButton.setEnabled(True)
else:
self.localDirFeedbackLabel.setStyleSheet("color: green;")

self.submitButton.setEnabled(True)
self.submitButton.setEnabled(True)

def on_local_dir_line_edit_editing_finished(self) -> None:
local_dir = self.localDirLineEdit.text()
Expand All @@ -550,44 +541,6 @@ def on_logout_button_clicked(self) -> None:
def on_refresh_button_clicked(self) -> None:
self.network_manager.projects_cache.refresh()

def local_dir_feedback(
self, local_dir, empty_ok=True, exiting_ok=True
) -> Tuple[LocalDirFeedback, str]:
if not local_dir:
return LocalDirFeedback.Error, self.tr(
"Please select local directory where the project to be stored."
)
elif not Path(local_dir).is_dir():
return LocalDirFeedback.Warning, self.tr(
"The entered path is not an existing directory. It will be created after you submit this form."
)
elif len(get_qgis_files_within_dir(Path(local_dir))) == 0:
message = self.tr(
"The entered path does not contain a QGIS project file yet."
)
status = LocalDirFeedback.Warning

if empty_ok:
status = LocalDirFeedback.Success
message += " "
message += self.tr("You can always add one later.")

return status, message
elif len(get_qgis_files_within_dir(Path(local_dir))) == 1:
message = self.tr("The entered path contains one QGIS project file.")
status = LocalDirFeedback.Warning

if exiting_ok:
status = LocalDirFeedback.Success
message += " "
message += self.tr("Exactly as it should be.")

return status, message
else:
return LocalDirFeedback.Error, self.tr(
"Multiple project files have been found in the directory. Please leave exactly one QGIS project in the root directory."
)

def show_projects(self) -> None:
self.feedbackLabel.setText("")
self.feedbackLabel.setVisible(False)
Expand Down Expand Up @@ -729,8 +682,8 @@ def select_local_dir(self) -> Optional[str]:
if local_dir == "":
return

feedback, feedback_msg = self.local_dir_feedback(
local_dir, empty_ok=False
feedback, feedback_msg = local_dir_feedback(
local_dir, no_project_status=LocalDirFeedback.Warning
)
title = self.tr("Cannot upload local QFieldSync directory")

Expand Down Expand Up @@ -763,8 +716,8 @@ def select_local_dir(self) -> Optional[str]:
# when the dir is empty, all is good. But if not there are some file, we need to ask the user to confirm what to do
if list(Path(local_dir).iterdir()):
buttons = QMessageBox.Ok | QMessageBox.Abort
feedback, feedback_msg = self.local_dir_feedback(
local_dir, exiting_ok=False
feedback, feedback_msg = local_dir_feedback(
local_dir, single_project_status=LocalDirFeedback.Warning
)
title = self.tr("QFieldSync checkout prefers an empty directory")
answer = None
Expand Down
45 changes: 29 additions & 16 deletions qfieldsync/ui/cloud_create_project_widget.ui
Original file line number Diff line number Diff line change
Expand Up @@ -162,6 +162,20 @@
</property>
</widget>
</item>
<item row="2" column="1">
<layout class="QGridLayout" name="localDirHBoxLayout">
<item row="0" column="1">
<widget class="QToolButton" name="dirnameButton">
<property name="text">
<string>...</string>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QLineEdit" name="dirnameLineEdit"/>
</item>
</layout>
</item>
<item row="2" column="0">
<widget class="QLabel" name="dirnameLabel">
<property name="text">
Expand All @@ -176,9 +190,6 @@
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QTextEdit" name="projectDescriptionTextEdit"/>
</item>
<item row="0" column="1">
<widget class="QLineEdit" name="projectNameLineEdit">
<property name="sizePolicy">
Expand All @@ -192,19 +203,21 @@
</property>
</widget>
</item>
<item row="2" column="1">
<layout class="QGridLayout" name="localDirHBoxLayout">
<item row="0" column="1">
<widget class="QToolButton" name="dirnameToolButton">
<property name="text">
<string>...</string>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QLineEdit" name="dirnameLineEdit"/>
</item>
</layout>
<item row="1" column="1">
<widget class="QTextEdit" name="projectDescriptionTextEdit"/>
</item>
<item row="3" column="1">
<widget class="QLabel" name="dirnameFeedbackLabel">
<property name="text">
<string/>
</property>
<property name="wordWrap">
<bool>true</bool>
</property>
<property name="textInteractionFlags">
<set>Qt::LinksAccessibleByMouse|Qt::TextSelectableByMouse</set>
</property>
</widget>
</item>
</layout>
</widget>
Expand Down
59 changes: 59 additions & 0 deletions qfieldsync/utils/cloud_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,19 @@


import re
from enum import Enum
from pathlib import Path
from typing import Tuple

from qgis.PyQt.QtCore import QObject

from qfieldsync.libqfieldsync.utils.qgis import get_qgis_files_within_dir


class LocalDirFeedback(Enum):
Error = "error"
Warning = "warning"
Success = "success"


def to_cloud_title(title):
Expand All @@ -35,3 +48,49 @@ def call(*args, **kwargs):
return call

return wrapper


def local_dir_feedback(
local_dir: str,
no_path_status: LocalDirFeedback = LocalDirFeedback.Error,
not_dir_status: LocalDirFeedback = LocalDirFeedback.Error,
not_existing_status: LocalDirFeedback = LocalDirFeedback.Warning,
no_project_status: LocalDirFeedback = LocalDirFeedback.Success,
single_project_status: LocalDirFeedback = LocalDirFeedback.Success,
multiple_projects_status: LocalDirFeedback = LocalDirFeedback.Error,
) -> Tuple[LocalDirFeedback, str]:
dummy = QObject()
if not local_dir:
return no_path_status, dummy.tr(
"Please select local directory where the project to be stored."
)
elif Path(local_dir).exists() and not Path(local_dir).is_dir():
return not_dir_status, dummy.tr(
"The entered path is not an directory. Please enter a valid directory path."
)
elif not Path(local_dir).exists():
return not_existing_status, dummy.tr(
"The entered path is not an existing directory. It will be created after you submit this form."
)
elif len(get_qgis_files_within_dir(Path(local_dir))) == 0:
message = dummy.tr("The entered path does not contain a QGIS project file yet.")
status = no_project_status

if single_project_status is not LocalDirFeedback.Success:
message += " "
message += dummy.tr("You can always add one later.")

return status, message
elif len(get_qgis_files_within_dir(Path(local_dir))) == 1:
message = dummy.tr("The entered path contains one QGIS project file.")
status = single_project_status

if single_project_status is not LocalDirFeedback.Success:
message += " "
message += dummy.tr("Exactly as it should be.")

return status, message
else:
return multiple_projects_status, dummy.tr(
"Multiple project files have been found in the directory. Please leave exactly one QGIS project in the root directory."
)

0 comments on commit 962dc2c

Please sign in to comment.