Login button component
RP start route path
The examples below all use /auth/logi/start as a placeholder. The actual path is up to the RP (for example, /auth/login, /sign-in, /api/auth/start). Replace it with your RP's own OAuth start route.
Standard size × theme combinations for the logi SSO button. Vanilla HTML + CSS variables — copy-paste it into any stack (React/Vue/Svelte/Flutter). Override the colors with tokens, and it works as-is.
Why we provide vanilla only
Per-framework NPM packages are planned for Phase 2, after we have adoption data. Until then, vanilla works in every stack, and when the design changes the RP can swap a single token line, which is the most flexible.
The QR login option is already integrated into logi's /oauth/authorize page, so no separate QR button is needed (see QR login).
Shared CSS
Drop this in once and all the sizes below work.
<style>
:root {
/* RP: override these to match your design system */
--logi-button-bg: #0F172A; /* dark theme bg */
--logi-button-fg: #F8FAFC; /* dark theme text */
--logi-button-bg-light: #FFFFFF;
--logi-button-fg-light: #0F172A;
--logi-button-border: rgba(15, 23, 42, 0.12);
--logi-button-radius: 0; /* Dcode design guide: border-radius 0 by default */
--logi-button-font: 'SUIT Variable', -apple-system, "Segoe UI", sans-serif;
}
.logi-btn {
display: inline-flex;
align-items: center;
justify-content: center;
gap: 0.5rem;
background: var(--logi-button-bg);
color: var(--logi-button-fg);
border: 1px solid var(--logi-button-border);
border-radius: var(--logi-button-radius);
font-family: var(--logi-button-font);
font-weight: 600;
text-decoration: none;
cursor: pointer;
transition: opacity 0.15s, transform 0.05s;
user-select: none;
}
.logi-btn:hover { opacity: 0.92; }
.logi-btn:active { transform: scale(0.98); }
.logi-btn--light {
background: var(--logi-button-bg-light);
color: var(--logi-button-fg-light);
}
/* sizes */
.logi-btn--1x1 { width: 44px; height: 44px; padding: 0; }
.logi-btn--2x1 { height: 44px; padding: 0 1rem; font-size: 0.9375rem; }
.logi-btn--4x1 { height: 56px; padding: 0 1.5rem; font-size: 1rem; width: 100%; }
.logi-btn__logo { width: 20px; height: 20px; flex-shrink: 0; }
.logi-btn--4x1 .logi-btn__logo { width: 24px; height: 24px; }
/* Style variants — a matter of taste. All three are supported; the web docs default is brand */
.logi-btn--brand { background: linear-gradient(135deg, #0088FF, #0041E6); color: #FFFFFF; }
.logi-btn--outline { background: transparent; color: inherit; border-color: var(--logi-button-border); }
</style>Brand icon:
🔴 canonical:
https://www.1pass.dev/icon.svg(public URL). Shared across every surface (web / iOS / Android / Flutter). The old three-concentric-circle SVG (<circle r="9">+r="4.5"+r="1.4">) pattern is deprecated (2026-05-19) — its weak brand recognition meant users did not recognize it as logi across RPs, causing confusion. Do not use concentric circles at any size.
# Download once during RP integration (into your RP's static asset location)
curl -o public/logi-icon.svg https://www.1pass.dev/icon.svg<!-- Web: reference the copy your RP hosts statically -->
<img class="logi-btn__logo" src="/logi-icon.svg" alt="" aria-hidden="true" />A reference without the actual file becomes a "silently empty icon"
If you put <img src="/logi-icon.svg"> in your markup but never place the static file, your SPA fallback or auth catch-all intercepts the path and returns a 302 redirect or HTML. <img> does not break the page on 404/302, so the button ships with an empty icon slot and no error anywhere (measured on axhub production, 2026-08-16 — /logi-icon.svg → 302 → /login HTML).
Always verify by machine after deploying:
curl -sI https://<your-rp>/logi-icon.svg | head -3
# Expect: HTTP 200 + content-type: image/svg+xml
# A 302 or text/html means the file is missing
# To compare bytes against the canonical:
curl -s https://<your-rp>/logi-icon.svg | md5
curl -s https://www.1pass.dev/icon.svg | md5 # must matchNative apps cannot use the SVG directly — per-platform asset pipelines:
| Surface | Guide |
|---|---|
| Web (HTML/CSS) | continue below on this page |
| iOS (SwiftUI) | Login button — iOS |
| Android (Compose) | Login button — Android |
Style variants — pick by taste
All three are supported. Which one to use is your RP's taste; this (web) page's default example is brand blue, while the app guides (iOS · Android) default to the neutral outline.
| Variant | Class | Light/dark behavior |
|---|---|---|
| Brand blue (web default example) | logi-btn--brand | Same in both modes — colors taken from the icon's dot gradient (#0088FF→#0041E6) |
| Inverting (former default) | logi-btn / logi-btn--light on dark backgrounds | Navy in light, flips to white in dark |
| Neutral outline (app default example) | logi-btn--outline | Canvas surface + border — balanced presence next to other SSO buttons |
1x1 — icon only (44×44)
Tight spaces like a sidebar / FAB / mobile header / action bar — logo only, no text.
<a href="/auth/logi/start" class="logi-btn logi-btn--1x1 logi-btn--brand" aria-label="Sign in with logi">
<img class="logi-btn__logo" src="/logi-icon.svg" alt="" aria-hidden="true" />
</a>Accessibility
The 1x1 button has no text, so aria-label="Sign in with logi" is required. If a screen reader cannot convey its meaning, it violates WCAG 2.1 4.1.2.
2x1 — inline (220×44)
Bottom of a login form / modal footer / "other ways to sign in" option group.
<a href="/auth/logi/start" class="logi-btn logi-btn--2x1 logi-btn--brand">
<img class="logi-btn__logo" src="/logi-icon.svg" alt="" aria-hidden="true" />
Sign in with logi
</a>4x1 — Hero (full-width × 56)
The primary CTA on the main login page. Takes up an entire row.
<a href="/auth/logi/start" class="logi-btn logi-btn--4x1 logi-btn--brand">
<img class="logi-btn__logo" src="/icon.svg" alt="" aria-hidden="true" />
Sign in with logi
</a>Design token override examples
To match your RP's design system:
/* Tailwind project */
:root {
--logi-button-bg: theme('colors.indigo.600');
--logi-button-fg: theme('colors.white');
--logi-button-radius: theme('borderRadius.md');
}
/* shadcn/ui */
:root {
--logi-button-bg: hsl(var(--primary));
--logi-button-fg: hsl(var(--primary-foreground));
--logi-button-radius: var(--radius);
}
/* Bootstrap */
:root {
--logi-button-bg: var(--bs-primary);
--logi-button-fg: #fff;
--logi-button-radius: var(--bs-border-radius);
}Framework inline (for reference)
React / JSX
// variant: "brand" (web default example) | "" (inverting dark) | "light" | "outline"
function LogiButton({ size = "2x1", variant = "brand", href = "/auth/logi/start" }) {
return (
<a href={href} className={`logi-btn logi-btn--${size} ${variant ? `logi-btn--${variant}` : ""}`}
aria-label="Sign in with logi">
<img className="logi-btn__logo" src="/icon.svg" alt="" aria-hidden="true" />
{size !== "1x1" && "Sign in with logi"}
</a>
);
}Svelte
<script>
// variant: "brand" (web default example) | "" (inverting dark) | "light" | "outline"
let { size = "2x1", variant = "brand", href = "/auth/logi/start" } = $props();
</script>
<a {href} class="logi-btn logi-btn--{size} {variant ? `logi-btn--${variant}` : ''}"
aria-label="Sign in with logi">
<img class="logi-btn__logo" src="/icon.svg" alt="" aria-hidden="true" />
{#if size !== "1x1"}Sign in with logi{/if}
</a>Flutter (logi_button.dart)
Planned to be split out into a dedicated SDK package. In the meantime, build the size matrix above yourself with flutter_web_auth_2 + IconButton/ElevatedButton. Use Theme.of(context).colorScheme.primary for the color.
Brand guide
| Item | Rule |
|---|---|
| Text | Korean: "logi 로 로그인" / English: "Sign in with logi" / Japanese: "logi でログイン" |
| Logo | /icon.svg (gradient dot) — use as-is. Do not transform, rotate, decompose colors, or use a concentric-circle substitute ❌ |
| Minimum size | 32×32px (smaller and the logo is hard to identify) |
| Clear space | Keep an empty margin around the button equal to half the logo's width |
| Color contrast | WCAG AA 4.5:1 or higher (using the light/dark tokens as-is satisfies this) |
Next (planned)
- NPM packages
@logi-auth/button-react/@logi-auth/button-vue/@logi-auth/button-svelte— Phase 2, after adoption data - CDN CSS
https://api.1pass.dev/buttons.css— one-line integration via<link rel="stylesheet"> - Figma library — for designer collaboration