Window Controls Overlay API: Custom PWA Title Bars
This article explores the Window Controls Overlay (WCO) API, a web technology that enables Progressive Web Apps (PWAs) on desktop operating systems to reclaim their top window area. You will learn how the API transforms default desktop window chrome into customizable canvas space, how to configure your Web App Manifest, and how to use JavaScript and CSS to position UI elements dynamically alongside native platform controls.
What is the Window Controls Overlay API?
Traditionally, desktop Progressive Web Apps display a reserved, full-width title bar containing native window controls (minimize, maximize, and close buttons) and the application title. This default behavior creates a visual distinction between web-based desktop apps and fully native applications.
The Window Controls Overlay API eliminates this dedicated title bar strip. Instead, it turns the window controls into a small, floating overlay anchored to the top corner of the window. The rest of the title bar area becomes standard web surface area, allowing developers to place custom navigation bars, search inputs, tabs, or branding directly in the top-level window frame.
Configuring the Web App Manifest
To activate the Window Controls Overlay, you must declare the feature
in your web app manifest file using the display_override
property:
{
"name": "Custom Titlebar PWA",
"display": "standalone",
"display_override": ["window-controls-overlay"]
}When installed, supported desktop browsers (such as Chrome or Edge on Windows, macOS, and Linux) will give users a toggle to expand web content into the title bar area.
Detecting Support and State with JavaScript
The navigator.windowControlsOverlay object provides the
JavaScript interface to interact with the title bar. You should first
check if the feature is supported by the user’s browser:
if ('windowControlsOverlay' in navigator) {
const isOverlayVisible = navigator.windowControlsOverlay.visible;
console.log(`Overlay visible: ${isOverlayVisible}`);
}The visible property returns a boolean indicating
whether the window controls are currently acting as an overlay over the
content area.
Querying Title Bar Geometry
To avoid placing interactive elements directly underneath the native
minimize/maximize/close buttons, JavaScript allows you to query the
exact available bounding rectangle of the title bar area using
getTitlebarAreaRect():
if ('windowControlsOverlay' in navigator && navigator.windowControlsOverlay.visible) {
const rect = navigator.windowControlsOverlay.getTitlebarAreaRect();
console.log(`Title bar dimensions: x=${rect.x}, y=${rect.y}, width=${rect.width}, height=${rect.height}`);
}This method returns a DOMRect representing the usable
region of the title bar (the space between or beside the native window
controls).
Responding to Dynamic Layout Changes
Desktop windows can be resized, snapped, or moved across monitors
with different scaling factors. Users can also toggle the overlay on and
off. The API provides a geometrychange event listener on
navigator.windowControlsOverlay so your application can
react instantly to bounding changes:
navigator.windowControlsOverlay.addEventListener('geometrychange', (event) => {
const rect = event.titlebarAreaRect;
const isVisible = event.visible;
updateCustomTitleBarLayout(rect, isVisible);
});
function updateCustomTitleBarLayout(rect, isVisible) {
const customHeader = document.querySelector('#custom-header');
if (isVisible) {
customHeader.style.paddingLeft = `${rect.x}px`;
customHeader.style.width = `${rect.width}px`;
customHeader.style.height = `${rect.height}px`;
} else {
customHeader.style.paddingLeft = '0px';
customHeader.style.width = '100%';
customHeader.style.height = 'auto';
}
}Making Custom Elements Draggable
Because standard title bar dragging behavior is disabled inside custom content areas, you must tell the browser which custom sections can be used to drag the window and which sections are interactive.
In CSS, use the non-standard -webkit-app-region
property:
.title-bar-container {
/* Allows the user to click and drag the desktop window */
-webkit-app-region: drag;
display: flex;
align-items: center;
height: env(titlebar-area-height, 32px);
}
.title-bar-container input,
.title-bar-container button {
/* Keeps buttons and inputs interactive */
-webkit-app-region: no-drag;
}Summary
The Window Controls Overlay API bridges the gap between web
applications and native desktop design. By configuring the
display_override field and leveraging the
navigator.windowControlsOverlay JavaScript interface
alongside CSS environment variables, developers can build responsive,
highly integrated title bars that fully utilize desktop screen real
estate.