OpenCPN chart plotter accessible from any device's browser no client install needed
2.2K
A containerized OpenCPN chart plotter, accessible from any device's browser — no client install needed. Built on Xpra (remote display, streamed over HTML5) with GPU-accelerated rendering via VirtualGL.
One image works across Intel, AMD, and Nvidia GPUs — or with no GPU at all — the
right path is detected automatically at container startup, no build-time choice
needed. A separate :pi image covers Raspberry Pi (arm64).
| Tag | Platform |
|---|---|
x86 | Intel/AMD/Nvidia GPUs, or CPU-only |
pi | Raspberry Pi (arm64) |
# compose.yaml
services:
opencpn:
image: npgause/opencpn-kiosk:x86
container_name: opencpn
restart: unless-stopped
network_mode: host # needed for NMEA/Signal K mDNS discovery - see "Networking" below
environment:
- XPRA_BIND_PORT=14500
- XPRA_DISPLAY=:100
devices:
- /dev/dri:/dev/dri # Intel/AMD GPU passthrough - omit for CPU-only
group_add:
- "993" # host's `render` group GID - `getent group render`
volumes:
- ./data:/home/ubuntu/.opencpn
docker compose up -d
Then open http://<host>:14500 in a browser.
For Nvidia, replace the devices:/group_add: lines above with:
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: 1
capabilities: [gpu]
(Requires nvidia-container-toolkit
installed and configured on the host.)
No GPU passed through at all is also fine — both OpenCPN's rendering and Xpra's video encoding fall back to software cleanly on their own.
There are two independent GPU consumers inside the container — OpenCPN's own rendering and Xpra's video encoding — and passing a GPU through doesn't force both to use it:
OPENCPN_USE_GPU | XPRA_USE_GPU | Result |
|---|---|---|
true (default) | true (default) | Both accelerated |
true | false | Rendering accelerated, encoding stays CPU |
false | true | Rendering stays CPU, encoding accelerated |
Set either to false in environment: to force that one consumer to stay
software even when a GPU is available.
| Variable | Default | Purpose |
|---|---|---|
OPENCPN_USE_GPU | true | Use the passed-through GPU for OpenCPN's rendering |
XPRA_USE_GPU | true | Use the passed-through GPU for Xpra's video encoding |
XPRA_BIND_PORT | 14500 | Port the HTML5 client listens on |
XPRA_DISPLAY | :100 | X11 display number Xpra uses internally |
XPRA_BIND_PORT/XPRA_DISPLAY only need changing if something else on the host
(another Xpra instance, another X server) is already using the default.
The example above uses network_mode: host so multicast/mDNS discovery works —
NMEA-network devices, Signal K server discovery, etc. Docker's default bridge
networking blocks multicast via NAT, which breaks that kind of discovery. If you
don't need it and prefer network isolation, use bridge networking instead with a
ports: mapping (e.g. "14500:14500") in place of network_mode: host.
OpenCPN's config, routes, and waypoints live in the volume mounted at
/home/ubuntu/.opencpn — rebuilding/updating the image never touches it. For
chart files, mount your own chart directory in separately, then point OpenCPN's
chart directory settings (Options > Charts) at that mounted path — nothing here
pre-configures a chart source for you.
Pin the device to a stable
path with a udev rule on the host (not /dev/ttyUSB0, which can renumber
across reboots), then map that stable path through via devices:.
Content type
Image
Digest
sha256:54fcf80fd…
Size
307 MB
Last updated
5 days ago
docker pull npgause/opencpn-kiosk:pi