diff --git a/mac/.gitignore b/mac/.gitignore index 69d030ab..23cfc637 100644 --- a/mac/.gitignore +++ b/mac/.gitignore @@ -33,6 +33,9 @@ VibeTunnel/Local.xcconfig # Build output build_output.txt +# Release state - temporary file +.release-state.json + # Sparkle private key - NEVER commit this! sparkle-private-ed-key.pem sparkle-private-key-KEEP-SECURE.txt diff --git a/web/src/client/components/session-view.ts b/web/src/client/components/session-view.ts index 4cce2227..014b1a02 100644 --- a/web/src/client/components/session-view.ts +++ b/web/src/client/components/session-view.ts @@ -93,6 +93,7 @@ export class SessionView extends LitElement { @state() private terminalTheme: TerminalThemeId = 'auto'; @state() private terminalContainerHeight = '100%'; @state() private isLandscape = false; + @state() private macAppConnected = false; private preferencesManager = TerminalPreferencesManager.getInstance(); @@ -199,6 +200,9 @@ export class SessionView extends LitElement { super.connectedCallback(); this.connected = true; + // Check server status to see if Mac app is connected + this.checkServerStatus(); + // Check initial orientation this.checkOrientation(); @@ -611,6 +615,11 @@ export class SessionView extends LitElement { } private handleScreenshare() { + // Only allow screenshare if Mac app is connected + if (!this.macAppConnected) { + logger.warn('Screenshare requested but Mac app is not connected'); + return; + } // Dispatch event to start screenshare this.dispatchEvent( new CustomEvent('start-screenshare', { @@ -620,6 +629,23 @@ export class SessionView extends LitElement { ); } + private async checkServerStatus() { + try { + const response = await fetch('/api/server/status', { + headers: authClient.getAuthHeader(), + }); + if (response.ok) { + const status = await response.json(); + this.macAppConnected = status.macAppConnected || false; + logger.debug('server status:', status); + } + } catch (error) { + logger.warn('failed to check server status:', error); + // Default to not connected if we can't check + this.macAppConnected = false; + } + } + private handleOpenSettings() { // Dispatch event to open settings modal this.dispatchEvent( @@ -1293,6 +1319,7 @@ export class SessionView extends LitElement { .onFontSizeChange=${(size: number) => this.handleFontSizeChange(size)} .onScreenshare=${() => this.handleScreenshare()} .onOpenSettings=${() => this.handleOpenSettings()} + .macAppConnected=${this.macAppConnected} @close-width-selector=${() => { this.showWidthSelector = false; this.customWidth = ''; diff --git a/web/src/client/components/session-view/mobile-menu.ts b/web/src/client/components/session-view/mobile-menu.ts index bf7bb4e0..d19f8058 100644 --- a/web/src/client/components/session-view/mobile-menu.ts +++ b/web/src/client/components/session-view/mobile-menu.ts @@ -26,6 +26,7 @@ export class MobileMenu extends LitElement { @property({ type: Function }) onMaxWidthToggle?: () => void; @property({ type: Function }) onOpenSettings?: () => void; @property({ type: String }) currentTheme: Theme = 'system'; + @property({ type: Boolean }) macAppConnected = false; @state() private showMenu = false; @state() private focusedIndex = -1; @@ -225,6 +226,7 @@ export class MobileMenu extends LitElement { } private renderDropdown() { + let menuItemIndex = 0; return html`
- - + + ${ + this.macAppConnected + ? html` + + ` + : '' + } - + ${ + this.macAppConnected + ? html` + + ` + : '' + }