Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
44 changes: 39 additions & 5 deletions datashuttle/tui/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,10 +14,7 @@
from textual.app import App, ComposeResult
from textual.binding import Binding
from textual.containers import Container
from textual.widgets import (
Button,
Label,
)
from textual.widgets import Button, Label

from datashuttle.configs import canonical_folders
from datashuttle.tui.screens import (
Expand Down Expand Up @@ -45,9 +42,12 @@ class TuiApp(App, inherit_bindings=False): # type: ignore
ENABLE_COMMAND_PALETTE = False

BINDINGS = [
Binding("ctrl+c", "app.quit", "Exit app", priority=True),
Binding("escape", "exit_app", "Exit app", priority=True),
Binding("ctrl+c", "show_copy_help", "Show copy help", priority=True),
]

exit_accept_or_decline_popup = False

def compose(self) -> ComposeResult:
"""Set up widgets for the main window."""
yield Container(
Expand All @@ -63,6 +63,7 @@ def compose(self) -> ComposeResult:
),
Button("Settings", id="mainwindow_settings_button"),
Button("Get Help", id="mainwindow_get_help_button"),
Button("Exit", id="mainwindow_exit_button"),
id="mainwindow_contents_container",
)

Expand Down Expand Up @@ -113,6 +114,39 @@ def on_button_pressed(self, event: Button.Pressed) -> None:
elif event.button.id == "mainwindow_validate_from_project_path":
self.push_screen(validate_at_path.ValidateScreen(self))

elif event.button.id == "mainwindow_exit_button":
self.app.exit()

def action_show_copy_help(self) -> None:
"""Display a notification (for CTRL+C)."""
self.notify(
"Use CTRL+Q to copy from Inputs and DirectoryTrees.\n"
"Use ESC or the 'Exit' button to quit the application.\n"
"CTRL+C can be used to copy after highlighting text with the mouse while pressing 'shift'.",
timeout=6,
)

def action_exit_app(self) -> None:
"""Show pop up to confirm closing the application."""
if self.exit_accept_or_decline_popup:
return

def exit_function(exit: bool) -> None:
self.exit_accept_or_decline_popup = False
if exit:
self.exit()

self.exit_accept_or_decline_popup = (
modal_dialogs.AcceptOrDeclineMessageBox(
self,
"Press 'Exit' to confirm closing datashuttle.",
"Exit",
"Cancel",
)
)

self.push_screen(self.exit_accept_or_decline_popup, exit_function)

def load_project_page(self, interface: Interface) -> None:
"""Load the project manager page.

Expand Down
36 changes: 36 additions & 0 deletions datashuttle/tui/css/tui_menu.tcss
Original file line number Diff line number Diff line change
Expand Up @@ -521,3 +521,39 @@ RenameFileOrFolderScreen {
#rename_screen_cancel_button {
align: center middle;
}

/* Accept or Decline Modal Popup ------------------------------------------------------------ */

AcceptOrDeclineMessageBox {
align: center middle;
content-align: center middle;
}

#accept_or_decline_messagebox_container {
align: center middle;
content-align: center middle;
height: 12;
width: 65;
border: tall $panel-lighten-1;
background: $primary-background;
}

AcceptOrDeclineMessageBox:light > #accept_or_decline_messagebox_container {
border: tall $panel-darken-3;
background: $boost;
}

#accept_or_decline_messagebox_label {
align: center middle;
text-align: center;
width: 100%;
margin: 0 0 1 2;
}

#accept_or_decline_messagebox_accept_button {
align: center middle;
}

#accept_or_decline_messagebox_decline_button {
align: center middle;
}
61 changes: 61 additions & 0 deletions datashuttle/tui/screens/modal_dialogs.py
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,67 @@ def on_button_pressed(self) -> None:
self.dismiss(True)


class AcceptOrDeclineMessageBox(ModalScreen):
"""Display generic pop up window to ask user to accept or decline."""

def __init__(
self,
mainwindow: TuiApp,
message: str,
accept_button_label: str,
decline_button_label: str,
) -> None:
"""Initialise the accept or decline pop up window.

Parameters
----------
mainwindow
Textual main app screen.

message
Message to show above the accept / decline button.

accept_button_label
Label to display on the 'accept' button.

decline_button_label
Label to display on the 'decline' button.

"""
super(AcceptOrDeclineMessageBox, self).__init__()

self.mainwindow = mainwindow
self.message = message
self.accept_button_label = accept_button_label
self.decline_button_label = decline_button_label

def compose(self) -> ComposeResult:
"""Add widgets to the RenameFileOrFolderScreen."""
yield Container(
Label(self.message, id="accept_or_decline_messagebox_label"),
Horizontal(
Button(
self.accept_button_label,
id="accept_or_decline_messagebox_accept_button",
),
Button(
self.decline_button_label,
id="accept_or_decline_messagebox_decline_button",
),
id="rename_screen_horizontal",
),
id="accept_or_decline_messagebox_container",
)

def on_button_pressed(self, event: Button.Pressed) -> None:
"""Handle button pressed on the RenameFileOrFolderScreen."""
if event.button.id == "accept_or_decline_messagebox_accept_button":
self.dismiss(True)

elif event.button.id == "accept_or_decline_messagebox_decline_button":
self.dismiss(False)


class ConfirmAndAwaitTransferPopup(ModalScreen):
"""A popup screen for confirming, awaiting and finishing a Transfer.

Expand Down
2 changes: 0 additions & 2 deletions datashuttle/tui/shared/validate_content.py
Original file line number Diff line number Diff line change
Expand Up @@ -155,8 +155,6 @@ def on_button_pressed(self, event: Button.Pressed) -> None:
"#validate_strict_mode_checkbox"
).value

# assert False, f"strict mode: {strict_mode}"

if self.interface:
if self.interface.project.is_local_project():
include_central = False
Expand Down
2 changes: 1 addition & 1 deletion docs/source/pages/user_guides/choose-a-terminal.md
Original file line number Diff line number Diff line change
Expand Up @@ -82,4 +82,4 @@ with rendering errors.
Once you've chosen a terminal, get started with
``datashuttle`` with our [Getting Started Tutorial](getting-started-walkthrough).

To quit ``datashuttle`` in the terminal, press `CTRL+C`.
To quit ``datashuttle`` in the terminal, press `CTRL+Q`.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should this be Esc?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks good catch!

2 changes: 1 addition & 1 deletion tests/tests_tui/test_tui_directorytree.py
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,7 @@ async def test_fill_and_append_next_sub_and_ses(self, setup_project_paths):
async def test_create_folders_directorytree_clipboard(
self, setup_project_paths
):
"""Check that pressing CTRL+Q on the directorytree copies the
"""Check that pressing CTRL+C on the directorytree copies the
hovered folder to the clipboard (using pyperclip).
"""
tmp_config_path, tmp_path, project_name = setup_project_paths.values()
Expand Down
Loading