Skip to content
API Documentation
BastionGuard™
RestoreWindow.vala
Go to the documentation of this file.
1/*
2 * RestoreWindow.vala
3 *
4 * Copyright 2012-2018 Tony George <teejeetech@gmail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19 * MA 02110-1301, USA.
20 *
21 */
22
23using Gtk;
24using Gee;
25
26using TeeJee.Logging;
31using TeeJee.System;
32using TeeJee.Misc;
33
34class RestoreWindow : Gtk.Window {
35
36 public signal void request_close();
37
38 private Gtk.Box root_box;
39 private Gtk.Box sidebar;
40 private Gtk.Box content_box;
41 private Gtk.Box header_box;
42 private Gtk.Box body_box;
43 private Gtk.Box bbox_action;
44 private Gtk.Stack page_stack;
45 private int current_page = -1;
46
47 // Sidebar nav
48 private Gtk.Button btn_nav_target;
49 private Gtk.Button btn_nav_check;
50 private Gtk.Button btn_nav_log;
51 private Gtk.Button btn_nav_users;
52 private Gtk.Button btn_nav_summary;
53 private Gtk.Button btn_nav_restore;
54 private Gtk.Button btn_nav_finish;
55 private Gtk.Button? current_nav_btn = null;
56
57 private Gtk.Label lbl_page_title;
58
59 // tabs
69
70 // actions
71 private Gtk.Button btn_prev;
72 private Gtk.Button btn_next;
73 private Gtk.Button btn_cancel;
74 private Gtk.Button btn_close;
75
76 private uint tmr_init;
77 private int def_width = 1080;
78 private int def_height = 720;
79 private bool success = false;
80
81 public bool check_before_restore = true;
82 private bool embedded_mode = false;
83
84 public RestoreWindow(bool embedded = false) {
85 embedded_mode = embedded;
86
87 log_debug("RestoreWindow: RestoreWindow()");
88
89 this.title = App.mirror_system ? _("Clone System") : _("Restore Snapshot");
90 if (!embedded_mode) this.modal = true;
91 this.set_default_size(def_width, def_height);
92 this.set_default_size(def_width, def_height);
93 this.set_icon_name("bastionguard-backup");
94 if (!embedded_mode) this.close_request.connect(on_close_request);
95
96 if (!embedded_mode) this.set_titlebar(HeaderFactory.create_main_headerbar(this, 220));
97
98 build_ui();
101
102 if (!embedded_mode)
103 show();
104
106
107 tmr_init = Timeout.add(100, init_delayed);
108
109 log_debug("RestoreWindow: RestoreWindow(): exit");
110 }
111
112 private void build_ui() {
113
114 root_box = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 0);
115 root_box.hexpand = true;
116 root_box.vexpand = true;
117 root_box.halign = Gtk.Align.FILL;
118 root_box.valign = Gtk.Align.FILL;
119 set_child(root_box);
120
123
124 root_box.append(sidebar);
125 root_box.append(content_box);
126 }
127
128 private void build_sidebar() {
129
130 sidebar = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
131 sidebar.set_size_request(220, -1);
132 sidebar.get_style_context().add_class("sidebar");
133 sidebar.hexpand = false;
134 sidebar.vexpand = true;
135 sidebar.halign = Gtk.Align.FILL;
136 sidebar.valign = Gtk.Align.FILL;
137
138 var sidebar_header = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 8);
139 sidebar_header.get_style_context().add_class("sidebar-header");
140 sidebar.append(sidebar_header);
141
142 Gtk.Widget logo_widget;
143 try {
144 logo_widget = new Gtk.Image.from_pixbuf(IconManager.lookup("bastionguard-backup", 48));
145 }
146 catch (Error e) {
147 logo_widget = themed_icon("document-open-recent-symbolic", 48);
148 }
149
150 var title = new Gtk.Label(_("BastionGuard™\nRestore"));
151 title.xalign = 0.0f;
152 title.get_style_context().add_class("sidebar-title");
153
154 sidebar_header.append(logo_widget);
155 sidebar_header.append(title);
156
157 sidebar.append(new Gtk.Box(Gtk.Orientation.VERTICAL, 0));
158
159 btn_nav_target = make_nav_button("drive-harddisk-symbolic", _("Target Device"));
160 btn_nav_check = make_nav_button("system-search-symbolic", _("Dry Run Check"));
161 btn_nav_log = make_nav_button("text-x-log-symbolic", _("Review Log"));
162 btn_nav_users = make_nav_button("system-users-symbolic", _("Users"));
163 btn_nav_summary = make_nav_button("document-properties-symbolic", _("Summary"));
164 btn_nav_restore = make_nav_button("view-refresh-symbolic", _("Restore"));
165 btn_nav_finish = make_nav_button("emblem-ok-symbolic", _("Finished"));
166
167 btn_nav_target.sensitive = false;
168 btn_nav_check.sensitive = false;
169 btn_nav_log.sensitive = false;
170 btn_nav_users.sensitive = false;
171 btn_nav_summary.sensitive = false;
172 btn_nav_restore.sensitive = false;
173 btn_nav_finish.sensitive = false;
174
175 var spacer = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
176 spacer.vexpand = true;
177 sidebar.append(spacer);
178 }
179
180 private Gtk.Button make_nav_button(string icon_name, string label_text) {
181
182 var btn = new Gtk.Button();
183 btn.get_style_context().add_class("sidebar-button");
184 btn.hexpand = true;
185 btn.margin_start = 8;
186 btn.margin_end = 8;
187 btn.margin_top = 2;
188 btn.margin_bottom = 2;
189
190 var row = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 10);
191 row.margin_start = 8;
192 row.margin_end = 8;
193 row.margin_top = 8;
194 row.margin_bottom = 8;
195
196 var img = themed_icon(icon_name, 18);
197 var lbl = new Gtk.Label(label_text);
198 lbl.xalign = 0.0f;
199
200 row.append(img);
201 row.append(lbl);
202
203 btn.set_child(row);
204 sidebar.append(btn);
205
206 return btn;
207 }
208
209 private void build_content() {
210
211 content_box = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
212 content_box.get_style_context().add_class("content");
213 content_box.hexpand = true;
214 content_box.vexpand = true;
215 content_box.halign = Gtk.Align.FILL;
216 content_box.valign = Gtk.Align.FILL;
217
218 header_box = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
219 header_box.margin_start = 20;
220 header_box.margin_end = 20;
221 header_box.margin_top = 20;
222 header_box.margin_bottom = 10;
223
224 lbl_page_title = new Gtk.Label(_("Restore Snapshot"));
225 lbl_page_title.xalign = 0.0f;
226 lbl_page_title.get_style_context().add_class("title");
228
229 body_box = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
230 body_box.margin_start = 14;
231 body_box.margin_end = 14;
232 body_box.margin_bottom = 12;
233 body_box.hexpand = true;
234 body_box.vexpand = true;
235
236 page_stack = new Gtk.Stack();
237 page_stack.hexpand = true;
238 page_stack.vexpand = true;
239 page_stack.halign = Gtk.Align.FILL;
240 page_stack.valign = Gtk.Align.FILL;
241
242 body_box.append(page_stack);
243
244 content_box.append(header_box);
245 content_box.append(body_box);
246 }
247
248 private Gtk.Widget wrap_page(Gtk.Widget child) {
249 var card = new Gtk.Box(Gtk.Orientation.VERTICAL, 0);
250 card.get_style_context().add_class("card");
251 card.hexpand = true;
252 card.vexpand = true;
253 card.margin_start = 6;
254 card.margin_end = 6;
255 card.margin_top = 6;
256 card.margin_bottom = 6;
257 card.append(child);
258 return card;
259 }
260
261 private void build_pages() {
262
263 Gtk.Label label;
264
265 label = new Gtk.Label(_("Restore Device"));
267 restore_device_box.margin_start = 12;
268 restore_device_box.margin_end = 12;
269 restore_device_box.margin_top = 12;
270 restore_device_box.margin_bottom = 12;
271 page_stack.add_named(wrap_page(restore_device_box), "target-device");
272
273 label = new Gtk.Label(_("Restore Exclude"));
275 restore_exclude_box.margin_start = 12;
276 restore_exclude_box.margin_end = 12;
277 restore_exclude_box.margin_top = 12;
278 restore_exclude_box.margin_bottom = 12;
279 page_stack.add_named(wrap_page(restore_exclude_box), "restore-exclude");
280
281 label = new Gtk.Label(_("Exclude Apps"));
283 exclude_apps_box.margin_start = 12;
284 exclude_apps_box.margin_end = 12;
285 exclude_apps_box.margin_top = 12;
286 exclude_apps_box.margin_bottom = 12;
287 page_stack.add_named(wrap_page(exclude_apps_box), "exclude-apps");
288
289 label = new Gtk.Label(_("Checking Restore Actions (Dry Run)"));
290 check_box = new RestoreBox(this);
291 check_box.margin_start = 0;
292 check_box.margin_end = 0;
293 check_box.margin_top = 0;
294 check_box.margin_bottom = 0;
295 page_stack.add_named(check_box, "check");
296
297 label = new Gtk.Label(_("Confirm Actions"));
298 log_box = new RsyncLogBox(this);
299 log_box.margin_start = 12;
300 log_box.margin_end = 12;
301 log_box.margin_top = 12;
302 log_box.margin_bottom = 12;
303 page_stack.add_named(wrap_page(log_box), "show-log");
304
305 label = new Gtk.Label(_("Users Home"));
306 var exclude_box = new ExcludeBox(this); // dummy - not used
307 users_box = new UsersBox(this, exclude_box, true);
308 users_box.margin_start = 12;
309 users_box.margin_end = 12;
310 users_box.margin_top = 12;
311 users_box.margin_bottom = 12;
312 page_stack.add_named(wrap_page(users_box), "users");
313
314 label = new Gtk.Label(_("Summary"));
315 summary_box = new RestoreSummaryBox(this);
316 summary_box.margin_start = 12;
317 summary_box.margin_end = 12;
318 summary_box.margin_top = 12;
319 summary_box.margin_bottom = 12;
320 page_stack.add_named(wrap_page(summary_box), "summary");
321
322 label = new Gtk.Label(_("Restore"));
323 restore_box = new RestoreBox(this);
324 restore_box.margin_start = 0;
325 restore_box.margin_end = 0;
326 restore_box.margin_top = 0;
327 restore_box.margin_bottom = 0;
328 page_stack.add_named(restore_box, "restore");
329
330 label = new Gtk.Label(_("Finished"));
332 restore_finish_box.margin_start = 12;
333 restore_finish_box.margin_end = 12;
334 restore_finish_box.margin_top = 12;
335 restore_finish_box.margin_bottom = 12;
336 page_stack.add_named(wrap_page(restore_finish_box), "finish");
337 }
338
339 private bool init_delayed() {
340
341 if (tmr_init > 0) {
342 Source.remove(tmr_init);
343 tmr_init = 0;
344 }
345
346 this.set_default_size(def_width, def_height);
347 go_first();
348
349 return false;
350 }
351
352 private bool on_close_request() {
353 save_changes();
354 return false;
355 }
356
357 private void save_changes() {
359 }
360
361 private void create_actions() {
362
363 var hbox = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 6);
364 content_box.append(hbox);
365
366 var bbox = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 8);
367 bbox.margin_start = 12;
368 bbox.margin_end = 12;
369 bbox.margin_top = 12;
370 bbox.margin_bottom = 12;
371 bbox.spacing = 6;
372 bbox.hexpand = true;
373 hbox.append(bbox);
374
375 bbox_action = bbox;
376
377 #if GTK3_18
378 bbox.halign = Gtk.Align.CENTER;
379 #endif
380
381 Gtk.SizeGroup size_group = null;
382
383 btn_prev = add_button(bbox, _("Previous"), "", size_group, null);
384 btn_prev.get_style_context().add_class("btn-back");
385 btn_prev.clicked.connect(() => {
386 go_prev();
387 });
388
389 btn_next = add_button(bbox, _("Next"), "", size_group, null);
390 btn_next.get_style_context().add_class("btn-next");
391 btn_next.clicked.connect(() => {
392 gtk_set_busy(true, this);
394 gtk_set_busy(false, this);
395 go_next();
396 });
397
398 btn_close = add_button(bbox, _("Cancel"), "", size_group, null);
399 btn_close.get_style_context().add_class("btn-cancel");
400 btn_close.get_style_context().add_class("btn-finish");
401 btn_close.clicked.connect(() => {
402 save_changes();
403 if (embedded_mode)
405 else
406 this.destroy();
407 });
408
409 btn_cancel = add_button(bbox, _("Cancel"), "", size_group, null);
410 btn_cancel.get_style_context().add_class("btn-cancel");
411 btn_cancel.clicked.connect(() => {
412
413 if (!App.dry_run) {
414 var title = _("Cancel restore?");
415 var msg = _("Cancelling the restore process will leave the target system in an inconsistent state. The system may fail to boot or you may run into various issues. After cancelling, you need to restore another snapshot, to bring the system to a consistent state. Click Yes to confirm.");
416
417 var dlg = new CustomMessageDialog(title, msg, Gtk.MessageType.ERROR, this, Gtk.ButtonsType.YES_NO);
418 var response = gtk_dialog_run(dlg);
419 dlg.destroy();
420
421 if (response != Gtk.ResponseType.YES) {
422 return;
423 }
424 }
425
426 if (App.task != null) {
427 App.task.stop(AppStatus.CANCELLED);
428 }
429
430 if (embedded_mode)
432 else
433 this.destroy();
434 });
435
436 btn_prev.hexpand = true;
437 btn_next.hexpand = true;
438 btn_cancel.hexpand = true;
439 btn_close.hexpand = true;
440
442 }
443
444 private void action_buttons_set_initial_visibility(bool visible) {
445 btn_prev.visible = visible;
446 btn_next.visible = visible;
447 btn_close.visible = visible;
448 btn_cancel.visible = visible;
449 }
450
451 // navigation ----------------------------------------------------
452
453 private void go_first() {
454
455 if (App.btrfs_mode) {
456 if (App.snapshot_to_restore.subvolumes.has_key("@home")) {
457 set_page(Tabs.USERS);
458 }
459 else {
460 set_page(Tabs.SUMMARY);
461 }
462 }
463 else {
464 set_page(Tabs.TARGET_DEVICE);
465 }
466
468 }
469
470 private void go_prev() {
471
472 switch (current_page) {
473 case Tabs.RESTORE_EXCLUDE:
474 set_page(Tabs.TARGET_DEVICE);
475 break;
476
477 case Tabs.EXCLUDE_APPS:
478 set_page(Tabs.RESTORE_EXCLUDE);
479 break;
480
481 case Tabs.SUMMARY:
482 if (App.btrfs_mode && App.snapshot_to_restore.subvolumes.has_key("@home")) {
483 set_page(Tabs.USERS);
484 }
485 else if (!App.btrfs_mode && check_before_restore) {
486 set_page(Tabs.SHOW_LOG);
487 }
488 else if (!App.btrfs_mode) {
489 set_page(Tabs.TARGET_DEVICE);
490 }
491 break;
492
493 case Tabs.SHOW_LOG:
494 set_page(Tabs.CHECK);
495 break;
496
497 case Tabs.USERS:
498 // disabilitato
499 break;
500
501 case Tabs.TARGET_DEVICE:
502 case Tabs.RESTORE:
503 case Tabs.FINISH:
504 break;
505 }
506
508 }
509
510 private void go_next() {
511
512 if (!validate_current_tab()) {
513 return;
514 }
515
516 switch (current_page) {
517 case Tabs.TARGET_DEVICE:
519 set_page(Tabs.CHECK);
520 }
521 else {
522 set_page(Tabs.SUMMARY);
523 }
524 break;
525
526 case Tabs.CHECK:
527 set_page(Tabs.SHOW_LOG);
528 break;
529
530 case Tabs.SHOW_LOG:
531 set_page(Tabs.SUMMARY);
532 break;
533
534 case Tabs.USERS:
535 set_page(Tabs.SUMMARY);
536 break;
537
538 case Tabs.SUMMARY:
539 set_page(Tabs.RESTORE);
540 break;
541
542 case Tabs.RESTORE:
543 set_page(Tabs.FINISH);
544 break;
545
546 case Tabs.FINISH:
547 destroy();
548 break;
549 }
550
553 }
554
555 private void initialize_tab() {
556
557 if (current_page < 0) {
558 return;
559 }
560
561 log_debug("initialize_tab: %d".printf(current_page));
562
564
565 switch (current_page) {
566 case Tabs.RESTORE:
567 case Tabs.CHECK:
568 btn_prev.hide();
569 btn_next.hide();
570 btn_close.hide();
571 btn_cancel.show();
572 btn_cancel.sensitive = true;
573 break;
574
575 case Tabs.TARGET_DEVICE:
576 case Tabs.RESTORE_EXCLUDE:
577 case Tabs.EXCLUDE_APPS:
578 case Tabs.SUMMARY:
579 case Tabs.USERS:
580 case Tabs.SHOW_LOG:
581 btn_prev.show();
582 btn_next.show();
583 btn_close.show();
584 btn_cancel.hide();
585
586 btn_prev.sensitive = false;
587 btn_next.sensitive = true;
588 btn_close.sensitive = true;
589 break;
590
591 case Tabs.FINISH:
592 btn_prev.show();
593 btn_next.show();
594 btn_close.show();
595 btn_cancel.hide();
596
597 btn_prev.sensitive = false;
598 btn_next.sensitive = false;
599 btn_close.sensitive = true;
600 break;
601 }
602
604
605 switch (current_page) {
606 case Tabs.TARGET_DEVICE:
608 break;
609
610 case Tabs.RESTORE_EXCLUDE:
612 break;
613
614 case Tabs.EXCLUDE_APPS:
616 break;
617
618 case Tabs.CHECK:
619 App.dry_run = true;
621 go_next();
622 return;
623
624 case Tabs.SHOW_LOG:
627 }
628 else {
629 set_page(Tabs.FINISH);
631 restore_finish_box.update_message(false, _("Error running Rsync"), "");
632 return;
633 }
634 break;
635
636 case Tabs.USERS:
638 break;
639
640 case Tabs.SUMMARY:
642 break;
643
644 case Tabs.RESTORE:
645 App.dry_run = false;
647 go_next();
648 return;
649
650 case Tabs.FINISH:
652 btn_close.label = _("Close");
653 break;
654 }
655
659 }
660
661 private bool validate_current_tab() {
662
663 if (current_page == Tabs.TARGET_DEVICE) {
664
666
667 if (ok) {
669 }
670
671 return ok;
672 }
673 else if (current_page == Tabs.RESTORE_EXCLUDE) {
675 }
676 else if (current_page == Tabs.EXCLUDE_APPS) {
678 }
679
680 return true;
681 }
682
683 private void clear_sidebar_selection() {
684 btn_nav_target.get_style_context().remove_class("active-sidebar-button");
685 btn_nav_check.get_style_context().remove_class("active-sidebar-button");
686 btn_nav_log.get_style_context().remove_class("active-sidebar-button");
687 btn_nav_users.get_style_context().remove_class("active-sidebar-button");
688 btn_nav_summary.get_style_context().remove_class("active-sidebar-button");
689 btn_nav_restore.get_style_context().remove_class("active-sidebar-button");
690 btn_nav_finish.get_style_context().remove_class("active-sidebar-button");
691 }
692
693 private void set_sidebar_active(Gtk.Button btn) {
694 btn.get_style_context().add_class("active-sidebar-button");
695 current_nav_btn = btn;
696 }
697
698 private void update_sidebar_state() {
699
701
702 switch (current_page) {
703 case Tabs.TARGET_DEVICE:
705 break;
706 case Tabs.CHECK:
708 break;
709 case Tabs.SHOW_LOG:
711 break;
712 case Tabs.USERS:
714 break;
715 case Tabs.SUMMARY:
717 break;
718 case Tabs.RESTORE:
720 break;
721 case Tabs.FINISH:
723 break;
724 }
725 }
726
727 private void update_page_title() {
728
729 switch (current_page) {
730 case Tabs.TARGET_DEVICE:
731 lbl_page_title.label = _("Select Restore Device");
732 break;
733 case Tabs.RESTORE_EXCLUDE:
734 lbl_page_title.label = _("Restore Exclude");
735 break;
736 case Tabs.EXCLUDE_APPS:
737 lbl_page_title.label = _("Exclude Apps");
738 break;
739 case Tabs.CHECK:
740 lbl_page_title.label = _("Checking Restore Actions");
741 break;
742 case Tabs.SHOW_LOG:
743 lbl_page_title.label = _("Review Log");
744 break;
745 case Tabs.USERS:
746 lbl_page_title.label = _("Users Home");
747 break;
748 case Tabs.SUMMARY:
749 lbl_page_title.label = _("Summary");
750 break;
751 case Tabs.RESTORE:
752 lbl_page_title.label = App.mirror_system ? _("Cloning System") : _("Restoring Snapshot");
753 break;
754 case Tabs.FINISH:
755 lbl_page_title.label = _("Finished");
756 break;
757 }
758 }
759
760 private void set_page(int page) {
761 current_page = page;
762 switch (page) {
763 case Tabs.TARGET_DEVICE:
764 page_stack.set_visible_child_name("target-device");
765 break;
766 case Tabs.RESTORE_EXCLUDE:
767 page_stack.set_visible_child_name("restore-exclude");
768 break;
769 case Tabs.EXCLUDE_APPS:
770 page_stack.set_visible_child_name("exclude-apps");
771 break;
772 case Tabs.CHECK:
773 page_stack.set_visible_child_name("check");
774 break;
775 case Tabs.SHOW_LOG:
776 page_stack.set_visible_child_name("show-log");
777 break;
778 case Tabs.USERS:
779 page_stack.set_visible_child_name("users");
780 break;
781 case Tabs.SUMMARY:
782 page_stack.set_visible_child_name("summary");
783 break;
784 case Tabs.RESTORE:
785 page_stack.set_visible_child_name("restore");
786 break;
787 case Tabs.FINISH:
788 page_stack.set_visible_child_name("finish");
789 break;
790 }
791 }
792
793 public enum Tabs {
794 // indexes here should match the order in which tabs were added to Notebook
795 TARGET_DEVICE = 0,
796 RESTORE_EXCLUDE = 1,
797 EXCLUDE_APPS = 2,
798 CHECK = 3,
799 SHOW_LOG = 4,
800 USERS = 5,
801 SUMMARY = 6,
802 RESTORE = 7,
803 FINISH = 8
804 }
805
806 public Gtk.Widget detach_root_widget() {
807 set_child(null);
808 return root_box;
809 }
810
811 // ── Icon theme support ─────────────────────────────────────────────────
812 private Gee.ArrayList<Gtk.Image> themed_img_list = new Gee.ArrayList<Gtk.Image>();
813 private Gee.ArrayList<string> themed_img_name = new Gee.ArrayList<string>();
814 private Gee.ArrayList<int> themed_img_size = new Gee.ArrayList<int>();
815
816 private Gtk.Image themed_icon(string icon_name, int size) {
817 var img = IconManager.lookup_image(icon_name, size);
818 themed_img_list.add(img);
819 themed_img_name.add(icon_name);
820 themed_img_size.add(size);
821 return img;
822 }
823
824 public void reload_themed_icons() {
825 for (int i = 0; i < themed_img_list.size; i++) {
826 var img = themed_img_list[i];
827 var name = themed_img_name[i];
828 var sz = themed_img_size[i];
829 var pix = IconManager.lookup(name, sz);
830 if (pix != null) {
831 img.set_from_pixbuf(pix);
832 } else {
833 img.set_from_icon_name(name);
834 }
835 }
836 }
837
838}
Main App
AppStatus
#define _(s)
void stop(AppStatus status_to_update=AppStatus.CANCELLED)
CustomMessageDialog(string _msg_title, string _msg_body, Gtk.MessageType _msg_type, Window? parent, Gtk.ButtonsType _buttons_type)
ExcludeAppsBox(Gtk.Window _parent_window)
ExcludeBox(Gtk.Window _parent_window)
static Gtk.HeaderBar create_main_headerbar(Gtk.Window win, int left_width=215)
static Gdk.? Pixbuf lookup(string icon_name, int icon_size, bool symbolic=false, bool use_hardcoded=false, int scale=1)
static Gtk.Image lookup_image(string icon_name, int icon_size, bool symbolic=false, bool use_hardcoded=false)
Snapshot snapshot_to_restore
Definition Main.vala:136
RsyncTask task
Definition Main.vala:160
void add_app_exclude_entries()
Definition Main.vala:766
bool btrfs_mode
Definition Main.vala:52
void cron_job_update()
Definition Main.vala:4463
void save_exclude_list_selections()
Definition Main.vala:1023
bool dry_run
Definition Main.vala:100
RestoreBox(Gtk.Window _parent_window)
bool restore()
RestoreDeviceBox(Gtk.Window _parent_window)
void refresh(bool reset_device_selections=true)
RestoreExcludeBox(Gtk.Window _parent_window)
RestoreFinishBox(Gtk.Window _parent_window)
void update_message(bool success, string message_header, string message_body)
RestoreSummaryBox(Gtk.Window _parent_window)
void update_sidebar_state()
void action_buttons_set_initial_visibility(bool visible)
Gtk.Button btn_nav_check
Gee.ArrayList< string > themed_img_name
RestoreSummaryBox summary_box
Gtk.Button btn_nav_users
Gtk.? Button current_nav_btn
RsyncLogBox log_box
Gee.ArrayList< Gtk.Image > themed_img_list
Gtk.Button btn_prev
Gtk.Widget detach_root_widget()
Gtk.Button btn_nav_log
Gee.ArrayList< int > themed_img_size
void reload_themed_icons()
void set_sidebar_active(Gtk.Button btn)
void clear_sidebar_selection()
RestoreBox restore_box
RestoreDeviceBox restore_device_box
Gtk.Button btn_nav_target
RestoreFinishBox restore_finish_box
Gtk.Widget wrap_page(Gtk.Widget child)
RestoreExcludeBox restore_exclude_box
Gtk.Button btn_nav_restore
signal void request_close()
Gtk.Button btn_nav_summary
Gtk.Button btn_next
Gtk.Button btn_nav_finish
RestoreBox check_box
Gtk.Button btn_close
ExcludeAppsBox exclude_apps_box
Gtk.Button make_nav_button(string icon_name, string label_text)
Gtk.Label lbl_page_title
Gtk.Stack page_stack
Gtk.Image themed_icon(string icon_name, int size)
bool validate_current_tab()
RestoreWindow(bool embedded=false)
Gtk.Button btn_cancel
void set_page(int page)
void open_log(string _rsync_log_file)
RsyncLogBox(Gtk.Window _window)
Gee.HashMap< string, Subvolume > subvolumes
Definition Snapshot.vala:46
string rsync_restore_log_file
UsersBox(Gtk.Window _parent_window, ExcludeBox _exclude_box, bool _restore_mode)
Definition UsersBox.vala:26
void refresh()
bool file_exists(string file_path)
void gtk_set_busy(bool busy, Gtk.Window win)
int gtk_dialog_run(Gtk.Dialog dlg)
void log_debug(string message)