A modern PHD2 guiding client built with Next.js 16, React 19, and Tauri 2.9. Provides a beautiful, responsive interface for controlling PHD2 autoguiding software via WebSocket JSON-RPC protocol.
- 🔭 Real-time Guide Monitoring - Live guide error charts, scatter plots, and correction pulse visualization
- ⭐ Star Selection - Auto-find or manual star selection with visual feedback
- 📊 Statistics Dashboard - RMS errors, peak-to-peak values, SNR, HFD tracking
- 🎯 Calibration Tools - Start, clear, flip calibration with status display
- 🌍 Polar Alignment - Drift alignment, static polar alignment, polar drift alignment tools
- 🌑 Dark Library - Build, load, and manage dark frame libraries
- 🔧 Defect Map - Create and manage bad pixel maps
- ⚙️ Algorithm Parameters - Fine-tune RA/Dec guiding algorithms
- 🔄 Lock Shift - Configure lock position shift for comet tracking
- 📝 Guiding Log - View and export detailed guiding logs
- 🎛️ Guide Settings - Dec guide mode, variable delay, search region configuration
- 💾 Frame Settings - Limit frame ROI, subframe settings
- 📊 Histogram Panel - Real-time image histogram analysis
- 🎯 Overlay System - Customizable crosshair, reticle, grid, and annotations
- ⌨️ Keyboard Shortcuts - Full keyboard control for all operations
- 📊 Performance Monitor - Real-time performance metrics
- 🖥️ Desktop & Mobile - Responsive design with PHD2-style desktop layout
- 🌓 Dark/Light Theme - System-aware theme switching
- 📱 Touch-friendly - Mobile navigation with swipe gestures
- 🎨 Modern UI - Built with shadcn/ui and Radix primitives
- 🖥️ Native Desktop - Cross-platform desktop app via Tauri
- 🛠️ Workflow Panel - One-click guided workflow
- 🔔 Notification Center - Centralized notification management
- 📏 Resizable Panels - Customizable panel layout
- Frontend: Next.js 16, React 19, TypeScript
- UI: Tailwind CSS v4, shadcn/ui, Radix UI, Lucide Icons
- State: Zustand
- Desktop: Tauri 2.9 (Rust)
- Testing: Jest, Playwright
- Protocol: WebSocket JSON-RPC 2.0 (PHD2 Event Server)
-
Node.js 20.x or later (Download)
-
pnpm 8.x or later (recommended)
npm install -g pnpm
- Rust 1.70 or later (Install)
- System Dependencies:
- Windows: Microsoft Visual Studio C++ Build Tools
- macOS: Xcode Command Line Tools
- Linux: See Tauri Prerequisites
# Clone the repository
git clone https://github.com/ElementAstro/cobalt-guider-client.git
cd cobalt-guider-client
# Install dependencies
pnpm install
# Verify installation
pnpm dev- Start PHD2 with Event Server enabled (default port 4400)
- Run
pnpm devand open http://localhost:3000 - Click "连接" (Connect) → Enter PHD2 host/port → "连接"
- Connect equipment via "连接设备"
- Loop - Click "循环曝光" to start camera preview
- Select Star - Click "自动选星" or click on preview to select
- Calibrate - Run calibration if needed (Calibration tab)
- Guide - Click "开始导星" to begin autoguiding
- Monitor - Watch real-time charts and statistics
For development without PHD2:
# Terminal 1: Start mock PHD2 server
pnpm mock-server
# Terminal 2: Start dev server
pnpm devThe mock server simulates:
- PHD2 WebSocket JSON-RPC 2.0 protocol
- Equipment connection (camera, mount)
- Looping exposures and star selection
- Guiding with realistic drift and seeing simulation
- Guide step events with RA/Dec errors and corrections
| Command | Description |
|---|---|
pnpm dev |
Start development server (port 3000) |
pnpm build |
Build for production |
pnpm start |
Start production server |
pnpm lint |
Run ESLint |
pnpm test |
Run unit tests (Jest) |
pnpm test:e2e |
Run E2E tests (Playwright) |
pnpm test:e2e:ui |
Run E2E tests with UI |
pnpm mock-server |
Start mock PHD2 server |
pnpm tauri dev |
Start Tauri desktop dev mode |
pnpm tauri build |
Build desktop application |
cobalt-guider-client/
├── app/ # Next.js App Router
│ ├── page.tsx # Main guider interface
│ ├── layout.tsx # Root layout
│ └── globals.css # Global styles (Tailwind v4)
├── components/
│ ├── guider/ # Guider-specific components (modular)
│ │ ├── advanced/ # Advanced settings
│ │ │ ├── algo-params.tsx # Algorithm parameters
│ │ │ ├── frame-settings.tsx # Frame/ROI settings
│ │ │ ├── guide-pulse.tsx # Manual guide pulse
│ │ │ ├── guide-settings.tsx # Dec mode, variable delay
│ │ │ ├── guiding-log.tsx # Guiding log viewer
│ │ │ └── lock-shift.tsx # Lock position shift (comet tracking)
│ │ ├── calibration/ # Calibration tools
│ │ │ ├── calibration-panel.tsx # Calibration controls
│ │ │ └── polar-alignment.tsx # Polar alignment tools
│ │ ├── connection/ # Connection management
│ │ │ ├── connection-panel.tsx # PHD2 connection
│ │ │ └── equipment-status.tsx # Equipment status display
│ │ ├── controls/ # Guiding controls
│ │ │ ├── guide-controls.tsx # Main control buttons
│ │ │ ├── quick-controls.tsx # Quick action buttons
│ │ │ └── workflow-panel.tsx # One-click workflow
│ │ ├── image/ # Image processing
│ │ │ ├── dark-library.tsx # Dark frame library
│ │ │ ├── defect-map.tsx # Bad pixel map
│ │ │ └── overlay-settings.tsx # Guide image overlay customization
│ │ ├── layout/ # Layout components
│ │ │ ├── header.tsx # App header
│ │ │ ├── mobile-nav.tsx # Mobile navigation
│ │ │ ├── floating-actions.tsx # Floating action buttons
│ │ │ ├── resizable-panel.tsx # Resizable panel system
│ │ │ └── status-bar.tsx # Status bar
│ │ ├── log/ # Logging & notifications
│ │ │ ├── event-log.tsx # Event log viewer
│ │ │ └── notification-center.tsx # Notification system
│ │ ├── preview/ # Preview & charts
│ │ │ ├── guide-preview.tsx # Guide camera preview
│ │ │ ├── guide-chart.tsx # Guide error chart
│ │ │ ├── scatter-plot.tsx # RA/Dec scatter plot
│ │ │ ├── correction-chart.tsx # Correction pulse chart
│ │ │ └── histogram-panel.tsx # Image histogram
│ │ ├── settings/ # Settings
│ │ │ ├── settings-dialog.tsx # Settings dialog
│ │ │ └── collapsible-panel.tsx # Collapsible panel wrapper
│ │ ├── stats/ # Statistics
│ │ │ ├── guide-stats.tsx # Guide statistics
│ │ │ └── stats-panel.tsx # Statistics panel
│ │ └── index.ts # Component exports
│ └── ui/ # shadcn/ui components (30+)
├── lib/
│ ├── guider/
│ │ └── overlay-renderer.ts # Canvas overlay rendering
│ ├── hooks/
│ │ ├── use-guide-data.ts # Guide data aggregation
│ │ ├── use-keyboard-shortcuts.ts # Keyboard shortcuts
│ │ ├── use-performance-monitor.ts # Performance monitoring
│ │ └── use-phd2.ts # PHD2 connection hook
│ ├── phd2/
│ │ ├── client.ts # PHD2 WebSocket client
│ │ └── events.ts # Event type guards & handlers
│ ├── stores/
│ │ ├── guider-store.ts # Main application state
│ │ └── overlay-store.ts # Overlay configuration state
│ ├── types/
│ │ ├── phd2.ts # PHD2 API types
│ │ └── overlay.ts # Overlay configuration types
│ ├── utils/
│ │ ├── export-utils.ts # Data export utilities
│ │ ├── toast-utils.ts # Toast notification helpers
│ │ └── validation-utils.ts # Input validation
│ └── utils.ts # General utilities
├── mock-server/
│ └── index.ts # Mock PHD2 server
├── tests/
│ └── e2e/
│ └── guider.spec.ts # E2E tests (Playwright)
├── docs/ # Documentation
│ ├── index.md # Documentation home
│ ├── architecture.md # Architecture overview
│ ├── overlay-system.md # Overlay system guide
│ ├── state-management.md # State management guide
│ ├── events.md # PHD2 events reference
│ ├── event-server.md # Event server protocol
│ ├── methods/ # PHD2 API methods
│ ├── components/ # Component documentation
│ └── user-guide/ # User guide
├── src-tauri/ # Tauri desktop app (Rust)
│ ├── src/ # Rust source
│ └── tauri.conf.json # Tauri configuration
└── package.json
Create a .env.local file for environment-specific variables:
# PHD2 connection defaults (optional)
NEXT_PUBLIC_PHD2_HOST=localhost
NEXT_PUBLIC_PHD2_PORT=4400Note: Only variables prefixed with NEXT_PUBLIC_ are exposed to the browser.
Edit src-tauri/tauri.conf.json to customize your desktop app:
{
"productName": "Cobalt Guider",
"version": "0.1.0",
"identifier": "com.elementastro.cobalt-guider",
"app": {
"windows": [
{
"title": "Cobalt Guider",
"width": 1280,
"height": 800,
"resizable": true
}
]
}
}import { Button } from "@/components/ui/button";
import { usePHD2 } from "@/lib/hooks/use-phd2";
import { useGuiderStore } from "@/lib/stores/guider-store";Available aliases:
@/components→components/@/lib→lib/@/ui→components/ui/
This client implements the PHD2 Event Server JSON-RPC 2.0 protocol.
| Category | Methods |
|---|---|
| Core | get_app_state, get_connected, set_connected, get_profiles, set_profile, shutdown |
| Equipment | get_exposure, set_exposure, get_current_equipment, get_cooler_status, set_cooler_state |
| Guiding | loop, stop_capture, find_star, guide, dither, set_paused, guide_pulse |
| Calibration | get_calibrated, clear_calibration, flip_calibration, get_calibration_data |
| Dark/Defect | start_dark_library_build, load_dark_library, start_defect_map_build, load_defect_map |
| Polar Align | start_drift_alignment, start_static_polar_alignment, start_polar_drift_alignment |
| Advanced | get_algo_param, set_algo_param, get_lock_shift_params, set_lock_shift_params |
| Event | Description |
|---|---|
Version |
Server version info on connect |
AppState |
Application state changes |
GuideStep |
Guide frame data with errors/corrections |
StarSelected |
Star selection confirmed |
StarLost |
Guide star lost |
Calibrating |
Calibration progress |
SettleDone |
Settle operation completed |
See docs/ for complete API documentation.
pnpm build
# Output: out/ directory - deploy to any static hostpnpm tauri build
# Output locations:
# Windows: src-tauri/target/release/bundle/msi/
# macOS: src-tauri/target/release/bundle/dmg/
# Linux: src-tauri/target/release/bundle/appimage/pnpm test # Run once
pnpm test:watch # Watch mode
pnpm test:coverage # With coverage# Requires mock server running
pnpm test:e2e # Run all E2E tests
pnpm test:e2e:ui # With Playwright UIE2E tests cover:
- Connection workflow
- Looping and star selection
- Guiding start/stop/pause
- Chart data display
- Mobile navigation
Cannot connect to PHD2
- Ensure PHD2 is running with Event Server enabled
- Check firewall settings for port 4400
- Verify host/port in connection dialog
WebSocket errors
- PHD2 Event Server uses
ws://notwss:// - Check if another client is connected
Port 3000 in use
# Windows
netstat -ano | findstr :3000
taskkill /PID <PID> /F
# macOS/Linux
lsof -ti:3000 | xargs kill -9Tauri build fails
pnpm tauri info # Check environment
rustup update # Update Rust
cd src-tauri && cargo clean # Clean cache- Fork the repository
- Create a feature branch (
git checkout -b feature/amazing-feature) - Commit changes (
git commit -m 'feat: add amazing feature') - Push to branch (
git push origin feature/amazing-feature) - Open a Pull Request
MIT License - see LICENSE for details.
- Check Troubleshooting
- Review PHD2 Documentation
- Open an issue on GitHub