Skip to content

Commit 9650bf4

Browse files
Optionally restore last session
Closes: #534
1 parent 69a53d4 commit 9650bf4

File tree

5 files changed

+65
-11
lines changed

5 files changed

+65
-11
lines changed

i18n/en/cosmic_files.ftl

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -171,6 +171,8 @@ show-details = Show details
171171
settings = Settings
172172
settings-tab = Tab
173173
settings-show-hidden = Show hidden files
174+
settings-general = General
175+
settings-restore-session = Restore session on start
174176
default-view = Default view
175177
icon-size-list = Icon size (list)
176178
icon-size-grid = Icon size (grid)

src/app.rs

Lines changed: 38 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ use crate::{
7171
tab::{self, HeadingOptions, ItemMetadata, Location, Tab, HOVER_DURATION},
7272
};
7373

74-
#[derive(Clone, Debug)]
74+
#[derive(Clone, Copy, Debug, PartialEq)]
7575
pub enum Mode {
7676
App,
7777
Desktop,
@@ -297,10 +297,12 @@ pub enum Message {
297297
Rename(Option<Entity>),
298298
ReplaceResult(ReplaceResult),
299299
RestoreFromTrash(Option<Entity>),
300+
SaveSession,
300301
SearchActivate,
301302
SearchClear,
302303
SearchInput(String),
303304
SearchSubmit,
305+
SessionConfig(crate::config::Session),
304306
SystemThemeModeChange(cosmic_theme::ThemeMode),
305307
TabActivate(Entity),
306308
TabNext,
@@ -1127,6 +1129,19 @@ impl App {
11271129
)
11281130
})
11291131
.into(),
1132+
widget::settings::view_section(fl!("settings-general"))
1133+
.add(
1134+
widget::settings::item::builder(fl!("settings-restore-session")).toggler(
1135+
self.config.session.restore,
1136+
move |restore| {
1137+
Message::SessionConfig(crate::config::Session {
1138+
restore,
1139+
..Default::default()
1140+
})
1141+
},
1142+
),
1143+
)
1144+
.into(),
11301145
])
11311146
.into()
11321147
}
@@ -2134,6 +2149,24 @@ impl Application for App {
21342149
self.operation(Operation::Restore { paths });
21352150
}
21362151
}
2152+
Message::SaveSession => {
2153+
if self.config.session.restore && self.mode == Mode::App {
2154+
let session = crate::config::Session {
2155+
tabs: Some(
2156+
self.tab_model
2157+
.iter()
2158+
.filter_map(|entity| {
2159+
self.tab_model
2160+
.data::<Tab>(entity)
2161+
.map(|tab| tab.location.clone())
2162+
})
2163+
.collect(),
2164+
),
2165+
..self.config.session
2166+
};
2167+
config_set!(session, session);
2168+
}
2169+
}
21372170
Message::SearchActivate => {
21382171
self.search_active = true;
21392172
return widget::text_input::focus(self.search_id.clone());
@@ -2163,6 +2196,9 @@ impl Application for App {
21632196
return self.search();
21642197
}
21652198
}
2199+
Message::SessionConfig(session) => {
2200+
config_set!(session, session);
2201+
}
21662202
Message::SystemThemeModeChange(_theme_mode) => {
21672203
return self.update_config();
21682204
}
@@ -2480,6 +2516,7 @@ impl Application for App {
24802516
if let Some(window_id) = self.window_id_opt.take() {
24812517
return Command::batch([
24822518
window::close(window_id),
2519+
Command::perform(async move { message::app(Message::SaveSession) }, |x| x),
24832520
Command::perform(async move { message::app(Message::MaybeExit) }, |x| x),
24842521
]);
24852522
}

src/config.rs

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ use serde::{Deserialize, Serialize};
1111

1212
use crate::{
1313
app::App,
14-
tab::{HeadingOptions, View},
14+
tab::{HeadingOptions, Location, View},
1515
};
1616

1717
pub const CONFIG_VERSION: u64 = 1;
@@ -97,6 +97,7 @@ pub struct Config {
9797
pub app_theme: AppTheme,
9898
pub favorites: Vec<Favorite>,
9999
pub tab: TabConfig,
100+
pub session: Session,
100101
}
101102

102103
impl Config {
@@ -142,6 +143,7 @@ impl Default for Config {
142143
Favorite::Videos,
143144
],
144145
tab: TabConfig::default(),
146+
session: Session::default(),
145147
}
146148
}
147149
}
@@ -212,3 +214,9 @@ impl IconSizes {
212214
percent!(self.grid, ICON_SIZE_GRID) as _
213215
}
214216
}
217+
218+
#[derive(Clone, Debug, Default, PartialEq, Eq, CosmicConfigEntry, Deserialize, Serialize)]
219+
pub struct Session {
220+
pub restore: bool,
221+
pub tabs: Option<Vec<Location>>,
222+
}

src/lib.rs

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -94,22 +94,29 @@ pub fn main() -> Result<(), Box<dyn std::error::Error>> {
9494

9595
localize::localize();
9696

97-
let (config_handler, config) = Config::load();
97+
let (config_handler, mut config) = Config::load();
9898

9999
let mut locations = Vec::new();
100100
for arg in env::args().skip(1) {
101-
let location = if &arg == "--trash" {
102-
Location::Trash
103-
} else {
104-
match fs::canonicalize(&arg) {
105-
Ok(absolute) => Location::Path(absolute),
101+
match &*arg {
102+
"--trash" => locations.push(Location::Trash),
103+
// Override session regardless of config
104+
"--no-session" => {
105+
_ = config.session.tabs.take();
106+
}
107+
path => {
108+
match fs::canonicalize(path) {
109+
Ok(absolute) => locations.push(Location::Path(absolute)),
106110
Err(err) => {
107111
log::warn!("failed to canonicalize {:?}: {}", arg, err);
108112
continue;
109113
}
110114
}
111-
};
112-
locations.push(location);
115+
}
116+
}
117+
}
118+
if let Some(session) = config.session.restore.then(|| config.session.tabs.take()).flatten() {
119+
locations.extend(session)
113120
}
114121

115122
let mut settings = Settings::default();

src/tab.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -771,7 +771,7 @@ pub fn scan_network(uri: &str, mounters: Mounters, sizes: IconSizes) -> Vec<Item
771771
Vec::new()
772772
}
773773

774-
#[derive(Clone, Debug, Eq, PartialEq)]
774+
#[derive(Clone, Debug, Eq, PartialEq, Deserialize, Serialize)]
775775
pub enum Location {
776776
Path(PathBuf),
777777
Search(PathBuf, String),

0 commit comments

Comments
 (0)