Skip to content

Commit ccccdea

Browse files
Merge pull request #1681 from CapSoftware/desktop-onboarding
New desktop onboarding experience
2 parents 17755dc + 4804fd1 commit ccccdea

File tree

10 files changed

+2454
-638
lines changed

10 files changed

+2454
-638
lines changed

apps/desktop/src-tauri/src/general_settings.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -149,6 +149,8 @@ pub struct GeneralSettingsStore {
149149
pub camera_window_position: Option<WindowPosition>,
150150
#[serde(default)]
151151
pub camera_window_positions_by_monitor_name: BTreeMap<String, WindowPosition>,
152+
#[serde(default = "default_true")]
153+
pub has_completed_onboarding: bool,
152154
}
153155

154156
fn default_enable_native_camera_preview() -> bool {
@@ -229,6 +231,7 @@ impl Default for GeneralSettingsStore {
229231
main_window_position: None,
230232
camera_window_position: None,
231233
camera_window_positions_by_monitor_name: BTreeMap::new(),
234+
has_completed_onboarding: false,
232235
}
233236
}
234237
}

apps/desktop/src-tauri/src/lib.rs

Lines changed: 46 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -638,6 +638,15 @@ async fn set_camera_input(
638638
drop(app);
639639

640640
if id == current_id && camera_in_use {
641+
if id.is_some() && !skip_camera_window.unwrap_or(false) {
642+
let show_result = ShowCapWindow::Camera { centered: false }
643+
.show(&app_handle)
644+
.await;
645+
show_result
646+
.map_err(|err| error!("Failed to show camera preview window: {err}"))
647+
.ok();
648+
}
649+
641650
return Ok(());
642651
}
643652

@@ -2693,16 +2702,19 @@ async fn reset_camera_permissions(_app: AppHandle) -> Result<(), String> {
26932702

26942703
#[tauri::command]
26952704
#[specta::specta]
2696-
#[instrument(skip(app))]
2697-
async fn reset_microphone_permissions(app: AppHandle) -> Result<(), ()> {
2698-
let bundle_id = app.config().identifier.clone();
2705+
#[instrument(skip(_app))]
2706+
async fn reset_microphone_permissions(_app: AppHandle) -> Result<(), String> {
2707+
#[cfg(target_os = "macos")]
2708+
{
2709+
let bundle_id = _app.config().identifier.clone();
26992710

2700-
Command::new("tccutil")
2701-
.arg("reset")
2702-
.arg("Microphone")
2703-
.arg(bundle_id)
2704-
.output()
2705-
.expect("Failed to reset microphone permissions");
2711+
Command::new("tccutil")
2712+
.arg("reset")
2713+
.arg("Microphone")
2714+
.arg(bundle_id)
2715+
.output()
2716+
.map_err(|_| "Failed to reset microphone permissions".to_string())?;
2717+
}
27062718

27072719
Ok(())
27082720
}
@@ -3336,7 +3348,7 @@ pub async fn run(recording_logging_handle: LoggingHandle, logs_dir: PathBuf) {
33363348
flags
33373349
})
33383350
.with_denylist(&[
3339-
CapWindowId::Setup.label().as_str(),
3351+
CapWindowId::Onboarding.label().as_str(),
33403352
CapWindowId::Main.label().as_str(),
33413353
"window-capture-occluder",
33423354
"target-select-overlay",
@@ -3501,18 +3513,24 @@ pub async fn run(recording_logging_handle: LoggingHandle, logs_dir: PathBuf) {
35013513
tokio::spawn({
35023514
let app = app.clone();
35033515
async move {
3504-
if !permissions.screen_recording.permitted()
3505-
|| !permissions.accessibility.permitted()
3506-
|| GeneralSettingsStore::get(&app)
3507-
.ok()
3508-
.flatten()
3509-
.map(|s| !s.has_completed_startup)
3510-
.unwrap_or(false)
3516+
let settings = GeneralSettingsStore::get(&app).ok().flatten();
3517+
let startup_completed = settings
3518+
.as_ref()
3519+
.map(|s| s.has_completed_startup)
3520+
.unwrap_or(false);
3521+
let onboarding_completed = settings
3522+
.as_ref()
3523+
.map(|s| s.has_completed_onboarding)
3524+
.unwrap_or(false);
3525+
3526+
if !startup_completed
3527+
|| !onboarding_completed
3528+
|| !permissions.necessary_granted()
35113529
{
3512-
let _ = ShowCapWindow::Setup.show(&app).await;
3530+
println!("Showing onboarding");
3531+
let _ = ShowCapWindow::Onboarding.show(&app).await;
35133532
} else {
3514-
println!("Permissions granted, showing main window");
3515-
3533+
println!("Showing main window");
35163534
let _ = ShowCapWindow::Main {
35173535
init_target_mode: None,
35183536
}
@@ -3864,12 +3882,18 @@ pub async fn run(recording_logging_handle: LoggingHandle, logs_dir: PathBuf) {
38643882
.run(move |_handle, event| match event {
38653883
#[cfg(target_os = "macos")]
38663884
tauri::RunEvent::Reopen { .. } => {
3885+
if let Some(onboarding) = CapWindowId::Onboarding.get(_handle) {
3886+
onboarding.show().ok();
3887+
onboarding.set_focus().ok();
3888+
return;
3889+
}
3890+
38673891
let has_window = _handle.webview_windows().iter().any(|(label, _)| {
38683892
label.starts_with("editor-")
38693893
|| label.starts_with("screenshot-editor-")
38703894
|| label.as_str() == "settings"
38713895
|| label.as_str() == "signin"
3872-
|| label.as_str() == "setup"
3896+
|| label.as_str() == "onboarding"
38733897
});
38743898

38753899
if has_window {
@@ -3881,7 +3905,7 @@ pub async fn run(recording_logging_handle: LoggingHandle, logs_dir: PathBuf) {
38813905
|| label.starts_with("screenshot-editor-")
38823906
|| label.as_str() == "settings"
38833907
|| label.as_str() == "signin"
3884-
|| label.as_str() == "setup"
3908+
|| label.as_str() == "onboarding"
38853909
})
38863910
.map(|(_, window)| window.clone())
38873911
{

apps/desktop/src-tauri/src/tray.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -330,8 +330,8 @@ fn get_current_mode(app: &AppHandle) -> RecordingMode {
330330
.unwrap_or_default()
331331
}
332332

333-
fn is_setup_window_open(app: &AppHandle) -> bool {
334-
app.webview_windows().contains_key("setup")
333+
fn is_onboarding_window_open(app: &AppHandle) -> bool {
334+
app.webview_windows().contains_key("onboarding")
335335
}
336336

337337
fn create_mode_submenu(app: &AppHandle) -> tauri::Result<Submenu<tauri::Wry>> {
@@ -365,7 +365,7 @@ fn create_mode_submenu(app: &AppHandle) -> tauri::Result<Submenu<tauri::Wry>> {
365365
}
366366

367367
fn build_tray_menu(app: &AppHandle, cache: &PreviousItemsCache) -> tauri::Result<Menu<tauri::Wry>> {
368-
if is_setup_window_open(app) {
368+
if is_onboarding_window_open(app) {
369369
return Menu::with_items(
370370
app,
371371
&[
@@ -809,7 +809,7 @@ pub fn create_tray(app: &AppHandle) -> tauri::Result<()> {
809809
Ok(TrayItem::RequestPermissions) => {
810810
let app = app.clone();
811811
tokio::spawn(async move {
812-
let _ = ShowCapWindow::Setup.show(&app).await;
812+
let _ = ShowCapWindow::Onboarding.show(&app).await;
813813
});
814814
}
815815
_ => {}

0 commit comments

Comments
 (0)