diff --git a/src/MainWindow.vala b/src/MainWindow.vala index 2faf178f8..b5bc47c5a 100644 --- a/src/MainWindow.vala +++ b/src/MainWindow.vala @@ -22,28 +22,25 @@ public interface UPower : GLib.Object { public abstract bool on_battery { owned get; set; } } -public class Installer.MainWindow : Gtk.Window { +public class Installer.MainWindow : Gtk.ApplicationWindow { // We have to do it step by step because the vala compiler has overflows with big numbers. private const uint64 ONE_GB = 1000 * 1000 * 1000; // Minimum 15 GB private const uint64 MINIMUM_SPACE = 15 * ONE_GB; private Gtk.Label infobar_label; - private Adw.Leaflet leaflet; + private Adw.NavigationView navigation_view; private LanguageView language_view; private TryInstallView try_install_view; + private KeyboardLayoutView keyboard_layout_view; private bool check_ignored = false; private uint orca_timeout_id = 0; construct { language_view = new LanguageView (); - leaflet = new Adw.Leaflet () { - can_navigate_back = true, - can_unfold = false, - homogeneous = false - }; - leaflet.append (language_view); + navigation_view = new Adw.NavigationView (); + navigation_view.add (language_view); infobar_label = new Gtk.Label ("") { use_markup = true @@ -63,13 +60,20 @@ public class Installer.MainWindow : Gtk.Window { battery_infobar.add_css_class (Granite.STYLE_CLASS_FRAME); var overlay = new Gtk.Overlay () { - child = leaflet + child = navigation_view }; overlay.add_overlay (battery_infobar); child = overlay; titlebar = new Gtk.Grid () { visible = false }; + var back_action = new SimpleAction ("back", null); + back_action.activate.connect (() => { + navigation_view.pop (); + }); + + add_action (back_action); + language_view.next_step.connect (() => { // Don't prompt for screen reader if we're able to navigate without it if (orca_timeout_id != 0) { @@ -128,136 +132,136 @@ public class Installer.MainWindow : Gtk.Window { return Source.REMOVE; }); - - leaflet.notify["visible-child"].connect (() => { - update_navigation (); - }); - - leaflet.notify["child-transition-running"].connect (() => { - update_navigation (); - }); - } - - private void update_navigation () { - if (!leaflet.child_transition_running) { - // We need to rebuild the views to reflect language changes and forking paths - if (leaflet.visible_child == language_view || leaflet.visible_child == try_install_view) { - while (leaflet.get_adjacent_child (FORWARD) != null) { - leaflet.remove (leaflet.get_adjacent_child (FORWARD)); - } - } - } } private void load_keyboard_view () { - var keyboard_layout_view = new KeyboardLayoutView (); + keyboard_layout_view = new KeyboardLayoutView (); try_install_view = new TryInstallView (); - leaflet.append (keyboard_layout_view); - leaflet.append (try_install_view); + navigation_view.push (keyboard_layout_view); - leaflet.visible_child = keyboard_layout_view; + keyboard_layout_view.next_step.connect (() => { + navigation_view.push (try_install_view); + }); try_install_view.custom_step.connect (() => { - load_check_view (); - load_partitioning_view (); - load_drivers_view (); - leaflet.navigate (FORWARD); + var check_view = load_check_view (); + if (check_view == null) { + load_partitioning_view (); + } else { + check_view.next_step.connect (() => { + load_partitioning_view (); + }); + }; }); try_install_view.next_step.connect (() => { - load_check_view (); - load_disk_view (); - load_encrypt_view (); - load_drivers_view (); - leaflet.navigate (FORWARD); + var check_view = load_check_view (); + if (check_view == null) { + load_disk_view (); + } else { + check_view.next_step.connect (() => { + load_disk_view (); + }); + }; }); } private void load_disk_view () { var disk_view = new DiskView (); - leaflet.append (disk_view); + navigation_view.push (disk_view); disk_view.load.begin (MINIMUM_SPACE); - disk_view.cancel.connect (() => leaflet.navigate (BACK)); + disk_view.next_step.connect (() => load_encrypt_view ()); } - private void load_check_view () { + private Installer.CheckView? load_check_view () { if (check_ignored) { - return; + return null; } var check_view = new Installer.CheckView (); if (check_view.has_messages) { - leaflet.append (check_view); - } + check_view.next_step.connect (() => { + check_ignored = true; + }); - check_view.cancel.connect (() => leaflet.navigate (BACK)); + navigation_view.push (check_view); - check_view.next_step.connect (() => { - check_ignored = true; - leaflet.navigate (FORWARD); - }); + return check_view; + } + + return null; } private void load_encrypt_view () { var encrypt_view = new EncryptView (); - leaflet.append (encrypt_view); + encrypt_view.next_step.connect (load_drivers_view); - encrypt_view.cancel.connect (() => { - leaflet.visible_child = try_install_view; - }); + navigation_view.push (encrypt_view); } private void load_partitioning_view () { var partitioning_view = new PartitioningView (MINIMUM_SPACE); - leaflet.append (partitioning_view); + navigation_view.push (partitioning_view); partitioning_view.next_step.connect (() => { unowned Configuration config = Configuration.get_default (); config.luks = (owned) partitioning_view.luks; config.mounts = (owned) partitioning_view.mounts; - leaflet.navigate (FORWARD); + load_drivers_view (); }); } private void load_drivers_view () { var drivers_view = new DriversView (); - leaflet.append (drivers_view); - drivers_view.next_step.connect (() => load_progress_view ()); + + navigation_view.push (drivers_view); } private void load_progress_view () { var progress_view = new ProgressView (); - leaflet.append (progress_view); - leaflet.visible_child = progress_view; - leaflet.can_navigate_back = false; + progress_view.on_success.connect (() => { + var success_view = new SuccessView (); + navigation_view.push (success_view); - progress_view.on_success.connect (() => load_success_view ()); + success_view.shown.connect (() => { + navigation_view.replace ({ success_view }); + }); + }); progress_view.on_error.connect (() => { load_error_view (progress_view.get_log ()); }); - progress_view.start_installation (); - } - private void load_success_view () { - var success_view = new SuccessView (); - leaflet.append (success_view); - leaflet.visible_child = success_view; + progress_view.shown.connect (() => { + navigation_view.replace ({ progress_view }); + }); + + navigation_view.push (progress_view); + progress_view.start_installation (); } private void load_error_view (string log) { var error_view = new ErrorView (log); - leaflet.append (error_view); - leaflet.visible_child = error_view; error_view.retry_install.connect (() => { - leaflet.visible_child = try_install_view; - leaflet.can_navigate_back = true; + navigation_view.replace ({ + language_view, + keyboard_layout_view, + try_install_view, + error_view + }); + navigation_view.pop (); + }); + + error_view.shown.connect (() => { + navigation_view.replace ({ error_view }); }); + + navigation_view.push (error_view); } private void set_infobar_string () { diff --git a/src/Views/AbstractInstallerView.vala b/src/Views/AbstractInstallerView.vala index 3fc30fe14..f0381f460 100644 --- a/src/Views/AbstractInstallerView.vala +++ b/src/Views/AbstractInstallerView.vala @@ -6,7 +6,7 @@ public abstract class AbstractInstallerView : Adw.NavigationPage { public bool cancellable { get; construct; } - public signal void cancel (); + public signal void next_step (); protected Gtk.Box title_area; protected Gtk.Box content_area; @@ -61,10 +61,9 @@ public abstract class AbstractInstallerView : Adw.NavigationPage { action_area.append (action_box_end); if (cancellable) { - var cancel_button = new Gtk.Button.with_label (_("Cancel Installation")); - cancel_button.clicked.connect (() => { - cancel (); - }); + var cancel_button = new Gtk.Button.with_label (_("Cancel Installation")) { + action_name = "win.back" + }; action_box_end.append (cancel_button); } diff --git a/src/Views/CheckView.vala b/src/Views/CheckView.vala index 06d26a501..d2d23d34c 100644 --- a/src/Views/CheckView.vala +++ b/src/Views/CheckView.vala @@ -25,8 +25,6 @@ public class Installer.CheckView : AbstractInstallerView { // Minimum 1GB public const uint64 MINIMUM_MEMORY = 1 * ONE_GB; - public signal void next_step (); - private Gtk.Box message_box; public bool has_messages { get { diff --git a/src/Views/DiskView.vala b/src/Views/DiskView.vala index 4ad9bc1ee..9ee4af95c 100644 --- a/src/Views/DiskView.vala +++ b/src/Views/DiskView.vala @@ -98,7 +98,7 @@ public class Installer.DiskView : AbstractInstallerView { sensitive = Installer.App.test_mode }; next_button.add_css_class (Granite.STYLE_CLASS_SUGGESTED_ACTION); - next_button.clicked.connect (() => ((Adw.Leaflet) get_parent ()).navigate (FORWARD)); + next_button.clicked.connect (() => next_step ()); action_box_end.append (next_button); } diff --git a/src/Views/DriversView.vala b/src/Views/DriversView.vala index 07f9bb3b7..af20ee9a2 100644 --- a/src/Views/DriversView.vala +++ b/src/Views/DriversView.vala @@ -16,8 +16,6 @@ */ public class DriversView : AbstractInstallerView { - public signal void next_step (); - construct { var image = new Gtk.Image.from_icon_name ("application-x-firmware") { pixel_size = 128 @@ -74,8 +72,9 @@ content_area.append (message_box); - var back_button = new Gtk.Button.with_label (_("Back")); - back_button.clicked.connect (() => ((Adw.Leaflet) get_parent ()).navigate (BACK)); + var back_button = new Gtk.Button.with_label (_("Back")) { + action_name = "win.back" + }; var next_button = new Gtk.Button.with_label (_("Erase and Install")); next_button.add_css_class (Granite.STYLE_CLASS_DESTRUCTIVE_ACTION); diff --git a/src/Views/EncryptView.vala b/src/Views/EncryptView.vala index cc6e8af06..5cefef71e 100644 --- a/src/Views/EncryptView.vala +++ b/src/Views/EncryptView.vala @@ -178,7 +178,7 @@ public class EncryptView : AbstractInstallerView { Configuration.get_default ().encryption_password = pw_entry.text; } - ((Adw.Leaflet) get_parent ()).navigate (FORWARD); + next_step (); }); pw_entry.changed.connect (() => { diff --git a/src/Views/KeyboardLayoutView.vala b/src/Views/KeyboardLayoutView.vala index 1efe77301..dc68a6e0e 100644 --- a/src/Views/KeyboardLayoutView.vala +++ b/src/Views/KeyboardLayoutView.vala @@ -52,7 +52,9 @@ public class KeyboardLayoutView : AbstractInstallerView { content_area.append (stack_box); - var back_button = new Gtk.Button.with_label (_("Back")); + var back_button = new Gtk.Button.with_label (_("Back")) { + action_name = "win.back" + }; var next_button = new Gtk.Button.with_label (_("Select")) { sensitive = false @@ -66,8 +68,6 @@ public class KeyboardLayoutView : AbstractInstallerView { next_button.activate (); }); - back_button.clicked.connect (() => ((Adw.Leaflet) get_parent ()).navigate (BACK)); - next_button.clicked.connect (() => { unowned Gtk.ListBoxRow row = input_variant_widget.main_listbox.get_selected_row (); if (row != null) { @@ -92,7 +92,7 @@ public class KeyboardLayoutView : AbstractInstallerView { return; } - ((Adw.Leaflet) get_parent ()).navigate (FORWARD); + next_step (); }); input_variant_widget.main_listbox.row_activated.connect ((row) => { diff --git a/src/Views/LanguageView.vala b/src/Views/LanguageView.vala index 1b881241e..c25bfea0b 100644 --- a/src/Views/LanguageView.vala +++ b/src/Views/LanguageView.vala @@ -27,8 +27,6 @@ public class Installer.LanguageView : AbstractInstallerView { private VariantWidget lang_variant_widget; - public signal void next_step (); - public LanguageView () { lang_timeout = GLib.Timeout.add_seconds (3, timeout); } diff --git a/src/Views/PartitioningView.vala b/src/Views/PartitioningView.vala index 628cbb63d..52cd8d51b 100644 --- a/src/Views/PartitioningView.vala +++ b/src/Views/PartitioningView.vala @@ -19,8 +19,6 @@ */ public class Installer.PartitioningView : AbstractInstallerView { - public signal void next_step (); - private Gtk.Button next_button; private Gtk.Button modify_partitions_button; private Gtk.Box disk_list; @@ -140,7 +138,9 @@ public class Installer.PartitioningView : AbstractInstallerView { modify_partitions_button = new Gtk.Button.with_label (_("Modify Partitions…")); modify_partitions_button.clicked.connect (() => open_partition_editor ()); - var back_button = new Gtk.Button.with_label (_("Back")); + var back_button = new Gtk.Button.with_label (_("Back")) { + action_name = "win.back" + }; next_button = new Gtk.Button.with_label (_("Next")); next_button.add_css_class (Granite.STYLE_CLASS_SUGGESTED_ACTION); @@ -150,7 +150,6 @@ public class Installer.PartitioningView : AbstractInstallerView { action_box_end.append (back_button); action_box_end.append (next_button); - back_button.clicked.connect (() => ((Adw.Leaflet) get_parent ()).navigate (BACK)); next_button.clicked.connect (() => next_step ()); } diff --git a/src/Views/TryInstallView.vala b/src/Views/TryInstallView.vala index ef3f09fe6..f6e0e938d 100644 --- a/src/Views/TryInstallView.vala +++ b/src/Views/TryInstallView.vala @@ -17,7 +17,6 @@ public class Installer.TryInstallView : AbstractInstallerView { public signal void custom_step (); - public signal void next_step (); construct { var type_image = new Gtk.Image.from_icon_name (Application.get_default ().application_id) { @@ -77,7 +76,9 @@ public class Installer.TryInstallView : AbstractInstallerView { content_area.append (type_scrolled); - var back_button = new Gtk.Button.with_label (_("Back")); + var back_button = new Gtk.Button.with_label (_("Back")) { + action_name = "win.back" + }; var next_button = new Gtk.Button.with_label (_("Next")) { sensitive = false @@ -87,8 +88,6 @@ public class Installer.TryInstallView : AbstractInstallerView { action_box_end.append (back_button); action_box_end.append (next_button); - back_button.clicked.connect (() => ((Adw.Leaflet) get_parent ()).navigate (BACK)); - demo_button.toggled.connect (() => { if (demo_button.active) { next_button.label = demo_button.title;