@excom/detect-browser
v0.1.3
Published
<detect-browser> custom element
Downloads
489
Maintainers
Readme
detect-browser
Drop-in tag provides browser, OS, device, and language metadata — target Safari, standalone mode, mobile devices, etc. Helpful in creating device-specific UX.
<div>
<detect-browser></detect-browser>
<style>
#demo-detect-browser-simple> :first-child {
detect-browser::before { content: "Rendered with CSS: "; }
detect-browser::after {
content:
"browser: " attr(browser-name) " " attr(browser-version)
" · engine: " attr(browser-engine)
" · os: " attr(operating-system)
" · device: " attr(device-type);
}
}
</style>
</div>Features
- Attribute metadata Set once on connect for CSS / Quark targeting
- Standalone / PWA detection
is-standalonereflects installed mode - Language detection
language-idreflects system-selected language - Device class
device-type(mobile/desktop) for coarse targeting - Full metadata
.provisionexposes user agent, languages, hardware hints
Installation
@excom/detect-browser v0.1.3
pnpm add @excom/detect-browsernpm install @excom/detect-browseryarn add @excom/detect-browserImport
import "@excom/detect-browser";Usage
Drop it anywhere and select on its attributes with plain CSS.
<detect-browser></detect-browser>html:has(detect-browser[browser-name="safari"]) .safari-only {
display: block;
}Live touch / pointer detection is detect-media media-query="(pointer: coarse)" — this element reports what the user agent says once, not what the input is now.
API Reference
Attributes
| Name | Surface | Type | Default | Values | Description |
| --- | --- | --- | --- | --- | --- |
| browser-name | state | string | | "chrome" | "firefox" | "safari" | "edge" | "opera" | internet explorer | Detected browser family. |
| browser-version | state | string | | | Browser version, as reported by the user agent string. |
| browser-engine | state | string | | "blink" | "gecko" | "webkit" | "trident" | Rendering engine. |
| browser-vendor | state | string | | | navigator.vendor, lowercased. |
| operating-system | state | string | | windows 10+ | windows 8.1 | windows 8 | windows 7 | macos <version> | "android" | "ios" | "linux" | Detected OS and, where available, version. |
| operating-platform | state | string | | | navigator.userAgentData.platform (falls back to navigator.platform), lowercased. |
| device-type | state | string | | "mobile" | "desktop" | Coarse device class inferred from the user agent string. |
| is-standalone | state | boolean | | | Present when running in standalone / installed PWA mode. |
| language-id | state | string | | | navigator.language, lowercased. |
| cookies-enabled | state | boolean | | | Present when navigator.cookieEnabled is true. |
| do-not-track | state | string | | | navigator.doNotTrack, as reported by the browser. |
Provision
| Name | Type | Description |
| --- | --- | --- |
| provision | BrowserInfo ({ browserName: string \| null; browserVersion: string \| null; browserEngine: string \| null; browserVendor: string \| null; operatingSystem: string \| null; operatingPlatform: string \| null; deviceType: string \| null; isStandalone: boolean \| null; languageId: string \| null; cookiesEnabled: boolean \| null; doNotTrack: string \| null; userAgent: string \| null; languageIds: string[] \| null; hardwareConcurrency: number \| null; deviceMemory: number \| null; }) | Every field above, plus values with no CSS-friendly attribute form: full user agent string, navigator.languages, hardware concurrency, and device memory (GB, where supported). Not reflected as an attribute. |
Examples
Language
Showing a greeting in your system language (Only Spanish or English for this example). language-id mirrors navigator.language (lowercased). Spanish prefixes show Hola; everything else shows Hello. Change the browser language (or override it in DevTools) and reload to flip it.
<div>
<detect-browser>
<span lang="en">Hello</span>
<span lang="es">Hola</span>
</detect-browser>
<style>
#demo-detect-browser-language > :first-child {
detect-browser {
[lang="en"],
[lang="es"] { display: none; }
&[language-id^="es"] [lang="es"],
&:not([language-id^="es"]) [lang="en"] { display: inline; }
}
}
</style>
</div>Safari-only install hint
iOS Safari has no install prompt, so the sheet renders "Add to Home Screen" steps there, and not once the app is installed. Spoof an iOS Safari user agent in DevTools and reload to trigger it.
<div>
<small role="note">Spoof an iOS Safari user agent in DevTools and reload.</small>
<detect-browser></detect-browser>
<include-content>
<template>
<p>Install this app: tap <strong>Share</strong>, then
<strong>Add to Home Screen</strong>.</p>
</template>
</include-content>
<quark-sheet>
detect-browser[browser-name="safari"][operating-system="ios"]:not([is-standalone]) + include-content {
is-active: "";
}
</quark-sheet>
</div>Release notes
0.1.1 (2026-09-23)
- Ship only dist (and declared extras) in the npm tarball; drop build logs, tests and sources
Full documentation: https://excom.dev/nucleus/packages/detect-browser
