mirror of
https://github.com/jhbruhn/respira.git
synced 2026-01-27 10:23:41 +00:00
feature: Add browser compatibility detection for Web Bluetooth
Detects if the browser supports Web Bluetooth API and displays an informative warning when unsupported. Provides users with clear options: use a compatible browser or download the desktop app. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
parent
1517c69595
commit
6cf491d921
2 changed files with 69 additions and 18 deletions
70
src/App.tsx
70
src/App.tsx
|
|
@ -12,6 +12,7 @@ import { BluetoothDevicePicker } from './components/BluetoothDevicePicker';
|
||||||
import { getErrorDetails } from './utils/errorCodeHelpers';
|
import { getErrorDetails } from './utils/errorCodeHelpers';
|
||||||
import { getStateVisualInfo } from './utils/machineStateHelpers';
|
import { getStateVisualInfo } from './utils/machineStateHelpers';
|
||||||
import { CheckCircleIcon, BoltIcon, PauseCircleIcon, ExclamationTriangleIcon, ArrowPathIcon, XMarkIcon, InformationCircleIcon } from '@heroicons/react/24/solid';
|
import { CheckCircleIcon, BoltIcon, PauseCircleIcon, ExclamationTriangleIcon, ArrowPathIcon, XMarkIcon, InformationCircleIcon } from '@heroicons/react/24/solid';
|
||||||
|
import { isBluetoothSupported } from './utils/bluetoothSupport';
|
||||||
import './App.css';
|
import './App.css';
|
||||||
|
|
||||||
function App() {
|
function App() {
|
||||||
|
|
@ -333,27 +334,60 @@ function App() {
|
||||||
<div className="flex-1 grid grid-cols-1 lg:grid-cols-[480px_1fr] gap-4 md:gap-5 lg:gap-6 lg:overflow-hidden">
|
<div className="flex-1 grid grid-cols-1 lg:grid-cols-[480px_1fr] gap-4 md:gap-5 lg:gap-6 lg:overflow-hidden">
|
||||||
{/* Left Column - Controls */}
|
{/* Left Column - Controls */}
|
||||||
<div className="flex flex-col gap-4 md:gap-5 lg:gap-6 lg:overflow-hidden">
|
<div className="flex flex-col gap-4 md:gap-5 lg:gap-6 lg:overflow-hidden">
|
||||||
{/* Connect Button - Show when disconnected */}
|
{/* Connect Button or Browser Hint - Show when disconnected */}
|
||||||
{!isConnected && (
|
{!isConnected && (
|
||||||
<div className="bg-white dark:bg-gray-800 p-4 rounded-lg shadow-md border-l-4 border-gray-400 dark:border-gray-600">
|
<>
|
||||||
<div className="flex items-start gap-3 mb-3">
|
{isBluetoothSupported() ? (
|
||||||
<div className="w-6 h-6 text-gray-600 dark:text-gray-400 flex-shrink-0 mt-0.5">
|
<div className="bg-white dark:bg-gray-800 p-4 rounded-lg shadow-md border-l-4 border-gray-400 dark:border-gray-600">
|
||||||
<svg className="w-6 h-6" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<div className="flex items-start gap-3 mb-3">
|
||||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M8.111 16.404a5.5 5.5 0 017.778 0M12 20h.01m-7.08-7.071c3.904-3.905 10.236-3.905 14.141 0M1.394 9.393c5.857-5.857 15.355-5.857 21.213 0" />
|
<div className="w-6 h-6 text-gray-600 dark:text-gray-400 flex-shrink-0 mt-0.5">
|
||||||
</svg>
|
<svg className="w-6 h-6" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
|
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M8.111 16.404a5.5 5.5 0 017.778 0M12 20h.01m-7.08-7.071c3.904-3.905 10.236-3.905 14.141 0M1.394 9.393c5.857-5.857 15.355-5.857 21.213 0" />
|
||||||
|
</svg>
|
||||||
|
</div>
|
||||||
|
<div className="flex-1 min-w-0">
|
||||||
|
<h3 className="text-sm font-semibold text-gray-900 dark:text-white mb-1">Get Started</h3>
|
||||||
|
<p className="text-xs text-gray-600 dark:text-gray-400">Connect to your embroidery machine</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<button
|
||||||
|
onClick={connect}
|
||||||
|
className="w-full flex items-center justify-center gap-2 px-3 py-2.5 sm:py-2 bg-blue-600 dark:bg-blue-700 text-white rounded font-semibold text-sm hover:bg-blue-700 dark:hover:bg-blue-600 active:bg-blue-800 dark:active:bg-blue-500 transition-colors cursor-pointer"
|
||||||
|
>
|
||||||
|
Connect to Machine
|
||||||
|
</button>
|
||||||
</div>
|
</div>
|
||||||
<div className="flex-1 min-w-0">
|
) : (
|
||||||
<h3 className="text-sm font-semibold text-gray-900 dark:text-white mb-1">Get Started</h3>
|
<div className="bg-amber-50 dark:bg-amber-900/20 p-4 rounded-lg shadow-md border-l-4 border-amber-500 dark:border-amber-600">
|
||||||
<p className="text-xs text-gray-600 dark:text-gray-400">Connect to your embroidery machine</p>
|
<div className="flex items-start gap-3">
|
||||||
|
<ExclamationTriangleIcon className="w-6 h-6 text-amber-600 dark:text-amber-400 flex-shrink-0 mt-0.5" />
|
||||||
|
<div className="flex-1 min-w-0">
|
||||||
|
<h3 className="text-base font-semibold text-amber-900 dark:text-amber-100 mb-2">Browser Not Supported</h3>
|
||||||
|
<p className="text-sm text-amber-800 dark:text-amber-200 mb-3">
|
||||||
|
Your browser doesn't support Web Bluetooth, which is required to connect to your embroidery machine.
|
||||||
|
</p>
|
||||||
|
<div className="space-y-2">
|
||||||
|
<p className="text-sm font-semibold text-amber-900 dark:text-amber-100">Please try one of these options:</p>
|
||||||
|
<ul className="text-sm text-amber-800 dark:text-amber-200 space-y-1.5 ml-4 list-disc">
|
||||||
|
<li>Use a supported browser (Chrome, Edge, or Opera)</li>
|
||||||
|
<li>
|
||||||
|
Download the Desktop app from{' '}
|
||||||
|
<a
|
||||||
|
href="https://github.com/jhbruhn/respira/releases/latest"
|
||||||
|
target="_blank"
|
||||||
|
rel="noopener noreferrer"
|
||||||
|
className="font-semibold underline hover:text-amber-900 dark:hover:text-amber-50 transition-colors"
|
||||||
|
>
|
||||||
|
GitHub Releases
|
||||||
|
</a>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
)}
|
||||||
<button
|
</>
|
||||||
onClick={connect}
|
|
||||||
className="w-full flex items-center justify-center gap-2 px-3 py-2.5 sm:py-2 bg-blue-600 dark:bg-blue-700 text-white rounded font-semibold text-sm hover:bg-blue-700 dark:hover:bg-blue-600 active:bg-blue-800 dark:active:bg-blue-500 transition-colors cursor-pointer"
|
|
||||||
>
|
|
||||||
Connect to Machine
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{/* Pattern File - Show during upload stage (before pattern is uploaded) */}
|
{/* Pattern File - Show during upload stage (before pattern is uploaded) */}
|
||||||
|
|
|
||||||
17
src/utils/bluetoothSupport.ts
Normal file
17
src/utils/bluetoothSupport.ts
Normal file
|
|
@ -0,0 +1,17 @@
|
||||||
|
/**
|
||||||
|
* Check if the current browser/environment supports Web Bluetooth API
|
||||||
|
* @returns true if Web Bluetooth is supported (or running in Electron), false otherwise
|
||||||
|
*/
|
||||||
|
export function isBluetoothSupported(): boolean {
|
||||||
|
// Always supported in Electron app
|
||||||
|
if (typeof window !== 'undefined' && (window as any).electronAPI) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check for Web Bluetooth API support in browser
|
||||||
|
if (typeof navigator !== 'undefined' && 'bluetooth' in navigator) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
Loading…
Reference in a new issue