Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve EditorDirDialog #86486

Merged
merged 1 commit into from
Jan 3, 2024
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
4 changes: 2 additions & 2 deletions editor/directory_create_dialog.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ void DirectoryCreateDialog::ok_pressed() {
err = da->make_dir_recursive(path);

if (err == OK) {
emit_signal(SNAME("dir_created"));
emit_signal(SNAME("dir_created"), base_dir.path_join(path));
} else {
EditorNode::get_singleton()->show_warning(TTR("Could not create folder."));
}
Expand All @@ -131,7 +131,7 @@ void DirectoryCreateDialog::config(const String &p_base_dir) {
}

void DirectoryCreateDialog::_bind_methods() {
ADD_SIGNAL(MethodInfo("dir_created"));
ADD_SIGNAL(MethodInfo("dir_created", PropertyInfo(Variant::STRING, "path")));
}

DirectoryCreateDialog::DirectoryCreateDialog() {
Expand Down
10 changes: 4 additions & 6 deletions editor/filesystem_dock.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1883,10 +1883,6 @@ Vector<String> FileSystemDock::_check_existing() {
return conflicting_items;
}

void FileSystemDock::_move_dialog_confirm(const String &p_path) {
_move_operation_confirm(p_path, move_dialog->is_copy_pressed());
}

void FileSystemDock::_move_operation_confirm(const String &p_to_path, bool p_copy, Overwrite p_overwrite) {
if (p_overwrite == OVERWRITE_UNDECIDED) {
to_move_path = p_to_path;
Expand Down Expand Up @@ -2363,6 +2359,7 @@ void FileSystemDock::_file_option(int p_option, const Vector<String> &p_selected
}
}
if (to_move.size() > 0) {
move_dialog->config(p_selected);
move_dialog->popup_centered_ratio(0.4);
}
} break;
Expand Down Expand Up @@ -3847,7 +3844,8 @@ FileSystemDock::FileSystemDock() {

move_dialog = memnew(EditorDirDialog);
add_child(move_dialog);
move_dialog->connect("dir_selected", callable_mp(this, &FileSystemDock::_move_dialog_confirm));
move_dialog->connect("move_pressed", callable_mp(this, &FileSystemDock::_move_operation_confirm).bind(false, OVERWRITE_UNDECIDED));
move_dialog->connect("copy_pressed", callable_mp(this, &FileSystemDock::_move_operation_confirm).bind(true, OVERWRITE_UNDECIDED));

overwrite_dialog = memnew(ConfirmationDialog);
add_child(overwrite_dialog);
Expand Down Expand Up @@ -3884,7 +3882,7 @@ FileSystemDock::FileSystemDock() {

make_dir_dialog = memnew(DirectoryCreateDialog);
add_child(make_dir_dialog);
make_dir_dialog->connect("dir_created", callable_mp(this, &FileSystemDock::_rescan));
make_dir_dialog->connect("dir_created", callable_mp(this, &FileSystemDock::_rescan).unbind(1));

make_scene_dialog = memnew(SceneCreateDialog);
add_child(make_scene_dialog);
Expand Down
15 changes: 8 additions & 7 deletions editor/filesystem_dock.h
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,12 @@ class FileSystemDock : public VBoxContainer {
FILE_SORT_MAX,
};

enum Overwrite {
OVERWRITE_UNDECIDED,
OVERWRITE_REPLACE,
OVERWRITE_RENAME,
};

private:
enum FileMenu {
FILE_OPEN,
Expand Down Expand Up @@ -133,12 +139,6 @@ class FileSystemDock : public VBoxContainer {
FILE_NEW_SCENE,
};

enum Overwrite {
OVERWRITE_UNDECIDED,
OVERWRITE_REPLACE,
OVERWRITE_RENAME,
};

HashMap<String, Color> folder_colors;
Dictionary assigned_folder_colors;

Expand Down Expand Up @@ -290,7 +290,6 @@ class FileSystemDock : public VBoxContainer {
void _duplicate_operation_confirm();
void _overwrite_dialog_action(bool p_overwrite);
Vector<String> _check_existing();
void _move_dialog_confirm(const String &p_path);
void _move_operation_confirm(const String &p_to_path, bool p_copy = false, Overwrite p_overwrite = OVERWRITE_UNDECIDED);

void _tree_rmb_option(int p_option);
Expand Down Expand Up @@ -410,4 +409,6 @@ class FileSystemDock : public VBoxContainer {
~FileSystemDock();
};

VARIANT_ENUM_CAST(FileSystemDock::Overwrite);

#endif // FILESYSTEM_DOCK_H
152 changes: 70 additions & 82 deletions editor/gui/editor_dir_dialog.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,22 +30,18 @@

#include "editor_dir_dialog.h"

#include "core/io/dir_access.h"
#include "core/os/keyboard.h"
#include "core/os/os.h"
#include "editor/directory_create_dialog.h"
#include "editor/editor_file_system.h"
#include "editor/editor_scale.h"
#include "editor/editor_settings.h"
#include "scene/gui/check_box.h"
#include "scene/gui/box_container.h"
#include "scene/gui/tree.h"
#include "servers/display_server.h"

void EditorDirDialog::_update_dir(TreeItem *p_item, EditorFileSystemDirectory *p_dir, const String &p_select_path) {
updating = true;

String path = p_dir->get_path();
const String path = p_dir->get_path();

p_item->set_metadata(0, p_dir->get_path());
p_item->set_metadata(0, path);
p_item->set_icon(0, tree->get_editor_theme_icon(SNAME("Folder")));
p_item->set_icon_modulate(0, tree->get_theme_color(SNAME("folder_icon_color"), SNAME("FileDialog")));

Expand All @@ -59,13 +55,33 @@ void EditorDirDialog::_update_dir(TreeItem *p_item, EditorFileSystemDirectory *p
p_item->set_text(0, p_dir->get_name());
}

if (path == new_dir_path || !p_item->get_parent()) {
p_item->select(0);
}

updating = false;
for (int i = 0; i < p_dir->get_subdir_count(); i++) {
TreeItem *ti = tree->create_item(p_item);
_update_dir(ti, p_dir->get_subdir(i));
}
}

void EditorDirDialog::config(const Vector<String> &p_paths) {
ERR_FAIL_COND(p_paths.is_empty());

if (p_paths.size() == 1) {
String path = p_paths[0];
if (path.ends_with("/")) {
path = path.substr(0, path.length() - 1);
}
// TRANSLATORS: %s is the file name that will be moved or duplicated.
set_title(vformat(TTR("Move/Duplicate: %s"), path.get_file()));
} else {
// TRANSLATORS: %d is the number of files that will be moved or duplicated.
set_title(vformat(TTRN("Move/Duplicate %d Item", "Move/Duplicate %d Items", p_paths.size()), p_paths.size()));
KoBeWi marked this conversation as resolved.
Show resolved Hide resolved
}
}

void EditorDirDialog::reload(const String &p_path) {
if (!is_visible()) {
must_reload = true;
Expand All @@ -76,13 +92,10 @@ void EditorDirDialog::reload(const String &p_path) {
TreeItem *root = tree->create_item();
_update_dir(root, EditorFileSystem::get_singleton()->get_filesystem(), p_path);
_item_collapsed(root);
new_dir_path.clear();
must_reload = false;
}

bool EditorDirDialog::is_copy_pressed() const {
return copy->is_pressed();
}

void EditorDirDialog::_notification(int p_what) {
switch (p_what) {
case NOTIFICATION_ENTER_TREE: {
Expand Down Expand Up @@ -112,14 +125,6 @@ void EditorDirDialog::_notification(int p_what) {
}
}

void EditorDirDialog::_copy_toggled(bool p_pressed) {
if (p_pressed) {
set_ok_button_text(TTR("Copy"));
} else {
set_ok_button_text(TTR("Move"));
}
}

void EditorDirDialog::_item_collapsed(Object *p_item) {
TreeItem *item = Object::cast_to<TreeItem>(p_item);

Expand All @@ -135,100 +140,83 @@ void EditorDirDialog::_item_collapsed(Object *p_item) {
}

void EditorDirDialog::_item_activated() {
_ok_pressed(); // From AcceptDialog.
TreeItem *ti = tree->get_selected();
ERR_FAIL_NULL(ti);
if (ti->get_child_count() > 0) {
ti->set_collapsed(!ti->is_collapsed());
}
}

void EditorDirDialog::ok_pressed() {
void EditorDirDialog::_copy_pressed() {
TreeItem *ti = tree->get_selected();
if (!ti) {
return;
}
ERR_FAIL_NULL(ti);

String dir = ti->get_metadata(0);
emit_signal(SNAME("dir_selected"), dir);
hide();
emit_signal(SNAME("copy_pressed"), ti->get_metadata(0));
}

void EditorDirDialog::_make_dir() {
void EditorDirDialog::ok_pressed() {
TreeItem *ti = tree->get_selected();
if (!ti) {
mkdirerr->set_text(TTR("Please select a base directory first."));
mkdirerr->popup_centered();
return;
}
ERR_FAIL_NULL(ti);

makedialog->popup_centered(Size2(250, 80));
makedirname->grab_focus();
hide();
emit_signal(SNAME("move_pressed"), ti->get_metadata(0));
}

void EditorDirDialog::_make_dir_confirm() {
void EditorDirDialog::_make_dir() {
TreeItem *ti = tree->get_selected();
if (!ti) {
return;
}

String dir = ti->get_metadata(0);

Ref<DirAccess> d = DirAccess::open(dir);
ERR_FAIL_COND_MSG(d.is_null(), "Cannot open directory '" + dir + "'.");

const String stripped_dirname = makedirname->get_text().strip_edges();
ERR_FAIL_NULL(ti);
makedialog->config(ti->get_metadata(0));
makedialog->popup_centered();
}

if (d->dir_exists(stripped_dirname)) {
mkdirerr->set_text(TTR("Could not create folder. File with that name already exists."));
mkdirerr->popup_centered();
return;
void EditorDirDialog::_make_dir_confirm(const String &p_path) {
// Multiple level of directories can be created at once.
String base_dir = p_path.get_base_dir();
while (true) {
opened_paths.insert(base_dir + "/");
if (base_dir == "res://") {
break;
}
base_dir = base_dir.get_base_dir();
}

Error err = d->make_dir(stripped_dirname);
if (err != OK) {
mkdirerr->popup_centered(Size2(250, 80) * EDSCALE);
} else {
opened_paths.insert(dir);
EditorFileSystem::get_singleton()->scan_changes(); // We created a dir, so rescan changes.
}
makedirname->set_text(""); // reset label
new_dir_path = p_path + "/";
EditorFileSystem::get_singleton()->scan_changes(); // We created a dir, so rescan changes.
}

void EditorDirDialog::_bind_methods() {
ADD_SIGNAL(MethodInfo("dir_selected", PropertyInfo(Variant::STRING, "dir")));
ADD_SIGNAL(MethodInfo("copy_pressed", PropertyInfo(Variant::STRING, "dir")));
ADD_SIGNAL(MethodInfo("move_pressed", PropertyInfo(Variant::STRING, "dir")));
}

EditorDirDialog::EditorDirDialog() {
set_title(TTR("Choose a Directory"));
set_hide_on_ok(false);

VBoxContainer *vb = memnew(VBoxContainer);
add_child(vb);

HBoxContainer *hb = memnew(HBoxContainer);
vb->add_child(hb);

hb->add_child(memnew(Label(TTR("Choose target directory:"))));
hb->add_spacer();

makedir = memnew(Button(TTR("Create Folder")));
hb->add_child(makedir);
makedir->connect("pressed", callable_mp(this, &EditorDirDialog::_make_dir));

tree = memnew(Tree);
vb->add_child(tree);
tree->set_v_size_flags(Control::SIZE_EXPAND_FILL);
tree->connect("item_activated", callable_mp(this, &EditorDirDialog::_item_activated));
KoBeWi marked this conversation as resolved.
Show resolved Hide resolved

copy = memnew(CheckBox);
vb->add_child(copy);
copy->set_text(TTR("Copy File(s)"));
copy->connect("toggled", callable_mp(this, &EditorDirDialog::_copy_toggled));
set_ok_button_text(TTR("Move"));

makedir = add_button(TTR("Create Folder"), DisplayServer::get_singleton()->get_swap_cancel_ok(), "makedir");
makedir->connect("pressed", callable_mp(this, &EditorDirDialog::_make_dir));
copy = add_button(TTR("Copy"), !DisplayServer::get_singleton()->get_swap_cancel_ok());
copy->connect("pressed", callable_mp(this, &EditorDirDialog::_copy_pressed));

makedialog = memnew(ConfirmationDialog);
makedialog->set_title(TTR("Create Folder"));
makedialog = memnew(DirectoryCreateDialog);
add_child(makedialog);

VBoxContainer *makevb = memnew(VBoxContainer);
makedialog->add_child(makevb);

makedirname = memnew(LineEdit);
makevb->add_margin_child(TTR("Name:"), makedirname);
makedialog->register_text_enter(makedirname);
makedialog->connect("confirmed", callable_mp(this, &EditorDirDialog::_make_dir_confirm));

mkdirerr = memnew(AcceptDialog);
mkdirerr->set_text(TTR("Could not create folder."));
add_child(mkdirerr);

set_ok_button_text(TTR("Move"));
makedialog->connect("dir_created", callable_mp(this, &EditorDirDialog::_make_dir_confirm));
}
15 changes: 7 additions & 8 deletions editor/gui/editor_dir_dialog.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,33 +33,32 @@

#include "scene/gui/dialogs.h"

class CheckBox;
class DirectoryCreateDialog;
class EditorFileSystemDirectory;
class Tree;
class TreeItem;

class EditorDirDialog : public ConfirmationDialog {
GDCLASS(EditorDirDialog, ConfirmationDialog);

ConfirmationDialog *makedialog = nullptr;
LineEdit *makedirname = nullptr;
AcceptDialog *mkdirerr = nullptr;
DirectoryCreateDialog *makedialog = nullptr;

Button *makedir = nullptr;
Button *copy = nullptr;
HashSet<String> opened_paths;
String new_dir_path;

Tree *tree = nullptr;
bool updating = false;
CheckBox *copy = nullptr;
timothyqiu marked this conversation as resolved.
Show resolved Hide resolved

void _copy_toggled(bool p_pressed);
void _item_collapsed(Object *p_item);
void _item_activated();
void _update_dir(TreeItem *p_item, EditorFileSystemDirectory *p_dir, const String &p_select_path = String());

void _make_dir();
void _make_dir_confirm();
void _make_dir_confirm(const String &p_path);

void _copy_pressed();
void ok_pressed() override;

bool must_reload = false;
Expand All @@ -69,8 +68,8 @@ class EditorDirDialog : public ConfirmationDialog {
static void _bind_methods();

public:
void config(const Vector<String> &p_paths);
void reload(const String &p_path = "");
bool is_copy_pressed() const;

EditorDirDialog();
};
Expand Down
Loading