From 5ad6921c6a09e3825904ce69e3f5071cad2e68c9 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Wed, 9 Oct 2024 16:24:34 +0100 Subject: [PATCH 01/10] Add "active-project-path" setting. * Sync with GitManager and ProjectChooserButton --- data/io.elementary.code.gschema.xml | 5 +++++ src/MainWindow.vala | 1 + src/Services/GitManager.vala | 5 +++-- src/Widgets/ChooseProjectButton.vala | 20 ++++++++++++-------- 4 files changed, 21 insertions(+), 10 deletions(-) diff --git a/data/io.elementary.code.gschema.xml b/data/io.elementary.code.gschema.xml index 400fe64e4..397b293ed 100644 --- a/data/io.elementary.code.gschema.xml +++ b/data/io.elementary.code.gschema.xml @@ -152,6 +152,11 @@ Remember the last focused document. Restore the focused document from a previous session when opening Code. + + '' + The active project path. + The path to the folder containing the active project. + '' The default build directory's relative path. diff --git a/src/MainWindow.vala b/src/MainWindow.vala index 431eeef82..319588e48 100644 --- a/src/MainWindow.vala +++ b/src/MainWindow.vala @@ -618,6 +618,7 @@ namespace Scratch { title = _("%s - %s").printf (doc.get_basename (), base_title); toolbar.set_document_focus (doc); + // FIXME Active project should not change just because selected document changes git_manager.active_project_path = doc.source_view.project.path; folder_manager_view.select_path (doc.file.get_path ()); diff --git a/src/Services/GitManager.vala b/src/Services/GitManager.vala index 6001473cf..04fe19a19 100644 --- a/src/Services/GitManager.vala +++ b/src/Services/GitManager.vala @@ -21,7 +21,7 @@ namespace Scratch.Services { public class GitManager : Object { public ListStore project_liststore { get; private set; } - public string active_project_path { get; set; default = "";} + public string active_project_path { get; set;} static Gee.HashMap project_gitrepo_map; static GitManager? instance; @@ -44,9 +44,10 @@ namespace Scratch.Services { return instance; } - private GitManager () { + construct { // Used to populate the ChooseProject popover in sorted order project_liststore = new ListStore (typeof (FolderManager.ProjectFolderItem)); + settings.bind ("active-project-path", this, "active-project-path", DEFAULT); } public MonitoredRepository? add_project (FolderManager.ProjectFolderItem root_folder) { diff --git a/src/Widgets/ChooseProjectButton.vala b/src/Widgets/ChooseProjectButton.vala index 79f597435..8a16acdb1 100644 --- a/src/Widgets/ChooseProjectButton.vala +++ b/src/Widgets/ChooseProjectButton.vala @@ -97,6 +97,11 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { popover = project_popover; var git_manager = Scratch.Services.GitManager.get_instance (); + set_active_path (git_manager.active_project_path); + git_manager.notify["active-project-path"].connect (() => { + set_active_path (git_manager.active_project_path); + }); + git_manager.project_liststore.items_changed.connect ((src, pos, n_removed, n_added) => { var rows = project_listbox.get_children (); for (int index = (int)pos; index < pos + n_removed; index++) { @@ -115,10 +120,6 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { set_active_path (git_manager.active_project_path); }); - git_manager.notify["active-project-path"].connect (() => { - set_active_path (git_manager.active_project_path); - }); - project_listbox.remove.connect ((row) => { var project_row = row as ProjectRow; var current_project = Scratch.Services.GitManager.get_instance ().active_project_path; @@ -140,12 +141,15 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { }); } + // Determine which docs are actually visible, terminal path, expanded folder etc private void set_active_path (string active_path) { foreach (var child in project_listbox.get_children ()) { - var project_entry = ((ProjectRow) child); - if (active_path.has_prefix (project_entry.project_path + Path.DIR_SEPARATOR_S)) { - project_listbox.row_activated (project_entry); - break; + var project_row = ((ProjectRow) child); + if (active_path.has_prefix (project_row.project_path)) { + project_row.active = true; + project_row.activate (); + } else { + project_row.active = false; } } } From 4eb037224f8a88ca1a0eb96fdb8da2de41fde094 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Wed, 9 Oct 2024 16:37:16 +0100 Subject: [PATCH 02/10] Dont change active project just because a document changes --- src/MainWindow.vala | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/MainWindow.vala b/src/MainWindow.vala index 319588e48..3dfc0efbc 100644 --- a/src/MainWindow.vala +++ b/src/MainWindow.vala @@ -618,8 +618,6 @@ namespace Scratch { title = _("%s - %s").printf (doc.get_basename (), base_title); toolbar.set_document_focus (doc); - // FIXME Active project should not change just because selected document changes - git_manager.active_project_path = doc.source_view.project.path; folder_manager_view.select_path (doc.file.get_path ()); // Must follow setting focus document for editorconfig plug From 67f238c0977d633e54dd260dfd36104838408c56 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Wed, 9 Oct 2024 16:43:57 +0100 Subject: [PATCH 03/10] Remove some unused code relating to active_project --- src/FolderManager/FileView.vala | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) diff --git a/src/FolderManager/FileView.vala b/src/FolderManager/FileView.vala index 684074922..22365cf16 100644 --- a/src/FolderManager/FileView.vala +++ b/src/FolderManager/FileView.vala @@ -61,11 +61,6 @@ public class Scratch.FolderManager.FileView : Code.Widgets.SourceList, Code.Pane public bool ignore_next_select { get; set; default = false; } public string icon_name { get; set; } public string title { get; set; } - public string active_project_path { - get { - return git_manager.active_project_path; - } - } public FileView (Scratch.Services.PluginsManager plugins_manager) { plugins = plugins_manager; @@ -193,14 +188,9 @@ public class Scratch.FolderManager.FileView : Code.Widgets.SourceList, Code.Pane selected = null; } - public void collapse_other_projects (string? keep_open_path = null) { + public void collapse_other_projects () { unowned string path; - if (keep_open_path == null) { - path = git_manager.active_project_path; - } else { - path = keep_open_path; - git_manager.active_project_path = path; - } + path = git_manager.active_project_path; foreach (var child in root.children) { var project_folder = ((ProjectFolderItem) child); From c05ab292bdd7ac80113217a6237ef4b8902ea624 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Sun, 13 Oct 2024 18:04:14 +0100 Subject: [PATCH 04/10] Do not override active project with default on startup --- src/Services/GitManager.vala | 3 +-- src/Widgets/ChooseProjectButton.vala | 6 ++++-- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/Services/GitManager.vala b/src/Services/GitManager.vala index 04fe19a19..ba7355265 100644 --- a/src/Services/GitManager.vala +++ b/src/Services/GitManager.vala @@ -73,8 +73,7 @@ namespace Scratch.Services { ); } - //Ensure active_project_path always set - active_project_path = root_path; + // No longer need to set default project (restored from settings or left unset) return project_gitrepo_map.@get (root_path); } diff --git a/src/Widgets/ChooseProjectButton.vala b/src/Widgets/ChooseProjectButton.vala index 8a16acdb1..6e61b61dd 100644 --- a/src/Widgets/ChooseProjectButton.vala +++ b/src/Widgets/ChooseProjectButton.vala @@ -146,8 +146,10 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { foreach (var child in project_listbox.get_children ()) { var project_row = ((ProjectRow) child); if (active_path.has_prefix (project_row.project_path)) { - project_row.active = true; - project_row.activate (); + if (!project_row.active) { + project_row.active = true; + project_row.activate (); + } } else { project_row.active = false; } From 5b4db0e1076c3debf84ee9196a2d2c1e07ed845d Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Sun, 13 Oct 2024 18:38:26 +0100 Subject: [PATCH 05/10] Show global search dialog if scope unspecified --- src/MainWindow.vala | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/MainWindow.vala b/src/MainWindow.vala index 3dfc0efbc..47f9c6273 100644 --- a/src/MainWindow.vala +++ b/src/MainWindow.vala @@ -1220,7 +1220,10 @@ namespace Scratch { term = search_bar.search_entry.text; } - folder_manager_view.search_global (get_target_path_for_actions (param), term); + // Do not try to "guess" intended path if it is not provided by action. The global + // search dialog will get it from user + string? search_path = param != null ? param.get_string () : null; + folder_manager_view.search_global (search_path, term); } private void update_find_actions () { From ad9cc13c1558ee2b6912101af4b7c361692a8530 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Mon, 14 Oct 2024 11:58:29 +0100 Subject: [PATCH 06/10] Distinguish global search path from default action target --- src/MainWindow.vala | 32 +++++++++++++++++++++++++++----- src/Services/Document.vala | 10 ++++++++++ src/Services/GitManager.vala | 2 +- 3 files changed, 38 insertions(+), 6 deletions(-) diff --git a/src/MainWindow.vala b/src/MainWindow.vala index 47f9c6273..5bac86abd 100644 --- a/src/MainWindow.vala +++ b/src/MainWindow.vala @@ -27,6 +27,17 @@ namespace Scratch { public Scratch.Application app { get; private set; } public bool restore_docs { get; construct; } public RestoreOverride restore_override { get; construct set; } + public string default_globalsearch_path { + owned get { + if (document_view.current_document != null) { + if (document_view.current_document.project_path != "") { + return document_view.current_document.project_path; + } + } + + return git_manager.active_project_path; + } + } public Scratch.Widgets.DocumentView document_view; @@ -1199,8 +1210,10 @@ namespace Scratch { } private void action_find_global (SimpleAction action, Variant? param) { + var selected_text = ""; + var search_path = ""; + var current_doc = get_current_document (); - string selected_text = ""; if (current_doc != null) { selected_text = current_doc.get_selected_text (false); } @@ -1220,10 +1233,19 @@ namespace Scratch { term = search_bar.search_entry.text; } - // Do not try to "guess" intended path if it is not provided by action. The global - // search dialog will get it from user - string? search_path = param != null ? param.get_string () : null; - folder_manager_view.search_global (search_path, term); + if (param != null && param.get_string () != "") { + search_path = param.get_string (); + } else { + search_path = default_globalsearch_path; + } + + if (search_path != "") { + folder_manager_view.search_global (search_path, term); + } else { + // Fallback to standard search + warning ("Unable to perform global search - search document instead"); + action_fetch (action, param); + } } private void update_find_actions () { diff --git a/src/Services/Document.vala b/src/Services/Document.vala index 2505959e1..02752e0df 100644 --- a/src/Services/Document.vala +++ b/src/Services/Document.vala @@ -65,6 +65,16 @@ namespace Scratch.Services { } } + public string project_path { + owned get { + if (source_view.project != null) { + return source_view.project.path; + } else { + return ""; + } + } + } + private string _title = ""; public string title { get { return _title; } diff --git a/src/Services/GitManager.vala b/src/Services/GitManager.vala index ba7355265..3b43bb88a 100644 --- a/src/Services/GitManager.vala +++ b/src/Services/GitManager.vala @@ -21,7 +21,7 @@ namespace Scratch.Services { public class GitManager : Object { public ListStore project_liststore { get; private set; } - public string active_project_path { get; set;} + public string active_project_path { get; set; default = "";} static Gee.HashMap project_gitrepo_map; static GitManager? instance; From 916e10d41067cd9888fcdc8bec00248e7fd72515 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Mon, 14 Oct 2024 12:25:33 +0100 Subject: [PATCH 07/10] Allow global search when no active project --- src/MainWindow.vala | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/MainWindow.vala b/src/MainWindow.vala index 5bac86abd..ff738b983 100644 --- a/src/MainWindow.vala +++ b/src/MainWindow.vala @@ -1256,9 +1256,9 @@ namespace Scratch { Utils.action_from_group (ACTION_SHOW_FIND, actions).set_enabled (is_current_doc); Utils.action_from_group (ACTION_FIND_NEXT, actions).set_enabled (is_current_doc); Utils.action_from_group (ACTION_FIND_PREVIOUS, actions).set_enabled (is_current_doc); + var can_global_search = is_current_doc || git_manager.active_project_path != null; + Utils.action_from_group (ACTION_FIND_GLOBAL, actions).set_enabled (can_global_search); - var is_active_project = git_manager.active_project_path != ""; - Utils.action_from_group (ACTION_FIND_GLOBAL, actions).set_enabled (is_active_project); return Source.REMOVE; }); } From ca34ddd98c249ad4863ff8c7c8b49060223074d0 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Mon, 14 Oct 2024 12:26:20 +0100 Subject: [PATCH 08/10] Set active project after load folder is none already set --- src/FolderManager/FileView.vala | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/FolderManager/FileView.vala b/src/FolderManager/FileView.vala index 8ce429615..0dfb2d52b 100644 --- a/src/FolderManager/FileView.vala +++ b/src/FolderManager/FileView.vala @@ -533,10 +533,15 @@ public class Scratch.FolderManager.FileView : Code.Widgets.SourceList, Code.Pane rename_items_with_same_name (child_folder); } } + Scratch.Services.GitManager.get_instance ().remove_project (folder_root); write_settings (); }); + if (Scratch.Services.GitManager.get_instance ().active_project_path == "" && folder_root.is_git_repo) { + Scratch.Services.GitManager.get_instance ().active_project_path = folder_root.path; + } + write_settings (); } From baf705e23a827a6e2a6375da8479959a1e181a25 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Mon, 14 Oct 2024 12:32:28 +0100 Subject: [PATCH 09/10] FileView: Use git_manager property --- src/FolderManager/FileView.vala | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/FolderManager/FileView.vala b/src/FolderManager/FileView.vala index 0dfb2d52b..1d823abcd 100644 --- a/src/FolderManager/FileView.vala +++ b/src/FolderManager/FileView.vala @@ -116,7 +116,7 @@ public class Scratch.FolderManager.FileView : Code.Widgets.SourceList, Code.Pane if (project_folder_item != folder_root) { toplevel_action_group.activate_action (MainWindow.ACTION_CLOSE_PROJECT_DOCS, new Variant.string (project_folder_item.path)); root.remove (project_folder_item); - Scratch.Services.GitManager.get_instance ().remove_project (project_folder_item); + git_manager.remove_project (project_folder_item); } } @@ -534,12 +534,12 @@ public class Scratch.FolderManager.FileView : Code.Widgets.SourceList, Code.Pane } } - Scratch.Services.GitManager.get_instance ().remove_project (folder_root); + git_manager.remove_project (folder_root); write_settings (); }); - if (Scratch.Services.GitManager.get_instance ().active_project_path == "" && folder_root.is_git_repo) { - Scratch.Services.GitManager.get_instance ().active_project_path = folder_root.path; + if (git_manager.active_project_path == "" && folder_root.is_git_repo) { + git_manager.active_project_path = folder_root.path; } write_settings (); From 43c1023cb7c2ee326709c533ce1075fd7b3e0c13 Mon Sep 17 00:00:00 2001 From: Jeremy Wootten Date: Wed, 30 Oct 2024 19:09:45 +0000 Subject: [PATCH 10/10] Allow no project to be restored. Only user sets active project. --- src/FolderManager/FileView.vala | 4 +- src/Widgets/ChooseProjectButton.vala | 90 ++++++++++------------------ 2 files changed, 33 insertions(+), 61 deletions(-) diff --git a/src/FolderManager/FileView.vala b/src/FolderManager/FileView.vala index 1d823abcd..a15dffbe1 100644 --- a/src/FolderManager/FileView.vala +++ b/src/FolderManager/FileView.vala @@ -538,9 +538,7 @@ public class Scratch.FolderManager.FileView : Code.Widgets.SourceList, Code.Pane write_settings (); }); - if (git_manager.active_project_path == "" && folder_root.is_git_repo) { - git_manager.active_project_path = folder_root.path; - } + // Do not assume this is the active folder write_settings (); } diff --git a/src/Widgets/ChooseProjectButton.vala b/src/Widgets/ChooseProjectButton.vala index 6e61b61dd..317c4b06d 100644 --- a/src/Widgets/ChooseProjectButton.vala +++ b/src/Widgets/ChooseProjectButton.vala @@ -18,18 +18,9 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { private const string NO_PROJECT_SELECTED = N_("No Project Selected"); + private const string PROJECT_TOOLTIP = N_("Active Git Project: %s"); private Gtk.Label label_widget; private Gtk.ListBox project_listbox; - public unowned Gtk.RadioButton? group_source { - get { - var first_row = project_listbox.get_row_at_index (0); - if (first_row != null) { - return ((ProjectRow)first_row).project_radio; - } else { - return null; - } - } - } public signal void project_chosen (); @@ -44,8 +35,6 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { xalign = 0.0f }; - tooltip_text = _("Active Git project: %s").printf (_(NO_PROJECT_SELECTED)); - var grid = new Gtk.Grid () { halign = Gtk.Align.START }; @@ -97,10 +86,6 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { popover = project_popover; var git_manager = Scratch.Services.GitManager.get_instance (); - set_active_path (git_manager.active_project_path); - git_manager.notify["active-project-path"].connect (() => { - set_active_path (git_manager.active_project_path); - }); git_manager.project_liststore.items_changed.connect ((src, pos, n_removed, n_added) => { var rows = project_listbox.get_children (); @@ -116,90 +101,78 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { project_listbox.insert (row, index); } } - - set_active_path (git_manager.active_project_path); }); project_listbox.remove.connect ((row) => { var project_row = row as ProjectRow; var current_project = Scratch.Services.GitManager.get_instance ().active_project_path; if (project_row.project_path == current_project) { - label_widget.label = _(NO_PROJECT_SELECTED); - label_widget.tooltip_text = _("Active Git project: %s").printf (_(NO_PROJECT_SELECTED)); Scratch.Services.GitManager.get_instance ().active_project_path = ""; + // Label and active_path will be updated automatically } }); project_listbox.row_activated.connect ((row) => { var project_entry = ((ProjectRow) row); - label_widget.label = project_entry.project_name; - var tooltip_text = Scratch.Utils.replace_home_with_tilde (project_entry.project_path); - label_widget.tooltip_text = _("Active Git project: %s").printf (tooltip_text); Scratch.Services.GitManager.get_instance ().active_project_path = project_entry.project_path; - project_entry.active = true; project_chosen (); }); + + realize.connect (() => { + set_active_path (git_manager.active_project_path); + git_manager.notify["active-project-path"].connect (() => { + set_active_path (git_manager.active_project_path); + }); + }); } - // Determine which docs are actually visible, terminal path, expanded folder etc + // Set appearance (only) of project chooser button and list according to active path private void set_active_path (string active_path) { foreach (var child in project_listbox.get_children ()) { var project_row = ((ProjectRow) child); - if (active_path.has_prefix (project_row.project_path)) { - if (!project_row.active) { - project_row.active = true; - project_row.activate (); - } - } else { - project_row.active = false; - } + // All paths must not end in directory separator so can be compared directly + project_row.active = active_path == project_row.project_path; + } + + if (active_path != "") { + label_widget.label = Path.get_basename (active_path); + tooltip_text = _(PROJECT_TOOLTIP).printf (Scratch.Utils.replace_home_with_tilde (active_path)); + } else { + label_widget.label = Path.get_basename (_(NO_PROJECT_SELECTED)); + tooltip_text = _(PROJECT_TOOLTIP).printf (_(NO_PROJECT_SELECTED)); } } private Gtk.Widget create_project_row (Scratch.FolderManager.ProjectFolderItem project_folder) { - var project_row = new ProjectRow (project_folder.file.file.get_path (), group_source); - // Handle renaming of project; - project_folder.bind_property ("name", project_row.project_radio, "label", BindingFlags.DEFAULT | BindingFlags.SYNC_CREATE, - (binding, srcval, ref targetval) => { - var label = srcval.get_string (); - targetval.set_string (label); - if (project_row.active) { - label_widget.label = label; - } - - return true; - } - ); + var project_path = project_folder.file.file.get_path (); + var project_row = new ProjectRow (project_path); + // Project folder items cannot be renamed in UI, no need to handle return project_row; } public class ProjectRow : Gtk.ListBoxRow { + private Gtk.CheckButton check_button; public bool active { get { - return project_radio.active; + return check_button.active; } set { - if (value) { - project_radio.active = true; - } + check_button.active = value; } } public string project_path { get; construct; } public string project_name { get { - return project_radio.label; + return check_button.label; } } - public Gtk.RadioButton project_radio { get; construct; } - - public ProjectRow (string project_path, Gtk.RadioButton? group_source ) { + public ProjectRow (string project_path) { Object ( - project_path: project_path, - project_radio: new Gtk.RadioButton.with_label_from_widget (group_source, Path.get_basename (project_path)) + project_path: project_path ); } @@ -208,8 +181,9 @@ public class Code.ChooseProjectButton : Gtk.MenuButton { } construct { - add (project_radio); - project_radio.button_release_event.connect (() => { + check_button = new Gtk.CheckButton.with_label (Path.get_basename (project_path)); + add (check_button); + check_button.button_release_event.connect (() => { activate (); return Gdk.EVENT_PROPAGATE; });