Accessibility improvements
This commit is contained in:
parent
b8df34309f
commit
d7bbf2b8e2
7 changed files with 47 additions and 26 deletions
|
@ -68,7 +68,7 @@ func newApplication(config *config) (*application, error) {
|
|||
|
||||
for w := range column.Widgets {
|
||||
widget := column.Widgets[w]
|
||||
app.widgetByID[widget.id()] = widget
|
||||
app.widgetByID[widget.GetID()] = widget
|
||||
|
||||
widget.setProviders(providers)
|
||||
}
|
||||
|
|
|
@ -284,7 +284,9 @@ function setupGroups() {
|
|||
|
||||
for (let i = 0; i < titles.length; i++) {
|
||||
titles[i].classList.remove("widget-group-title-current");
|
||||
titles[i].setAttribute("aria-selected", "false");
|
||||
tabs[i].classList.remove("widget-group-content-current");
|
||||
tabs[i].setAttribute("aria-hidden", "true");
|
||||
}
|
||||
|
||||
if (current < t) {
|
||||
|
@ -296,7 +298,9 @@ function setupGroups() {
|
|||
current = t;
|
||||
|
||||
title.classList.add("widget-group-title-current");
|
||||
title.setAttribute("aria-selected", "true");
|
||||
tabs[t].classList.add("widget-group-content-current");
|
||||
tabs[t].setAttribute("aria-hidden", "false");
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -670,6 +674,7 @@ async function setupPage() {
|
|||
setupLazyImages();
|
||||
} finally {
|
||||
pageElement.classList.add("content-ready");
|
||||
pageElement.setAttribute("aria-busy", "false");
|
||||
|
||||
for (let i = 0; i < contentReadyCallbacks.length; i++) {
|
||||
contentReadyCallbacks[i]();
|
||||
|
|
|
@ -110,7 +110,7 @@
|
|||
.visited-indicator:not(.text-truncate)::after,
|
||||
.visited-indicator.text-truncate::before,
|
||||
.bookmarks-link:not(.bookmarks-link-no-arrow)::after {
|
||||
content: '↗';
|
||||
content: '↗' / "";
|
||||
margin-left: 0.5em;
|
||||
display: inline-block;
|
||||
position: relative;
|
||||
|
@ -189,7 +189,7 @@
|
|||
}
|
||||
|
||||
.expand-toggle-button-icon::before {
|
||||
content: '';
|
||||
content: '' / "";
|
||||
font-size: 0.8rem;
|
||||
transform: rotate(90deg);
|
||||
line-height: 1;
|
||||
|
@ -341,6 +341,19 @@ html, body, .body-content {
|
|||
height: 100%;
|
||||
}
|
||||
|
||||
h1, h2, h3, h4, h5 {
|
||||
font: inherit;
|
||||
}
|
||||
|
||||
.visually-hidden {
|
||||
clip-path: inset(50%);
|
||||
height: 1px;
|
||||
overflow: hidden;
|
||||
position: absolute;
|
||||
white-space: nowrap;
|
||||
width: 1px;
|
||||
}
|
||||
|
||||
a {
|
||||
text-decoration: none;
|
||||
color: inherit;
|
||||
|
@ -563,7 +576,7 @@ kbd:active {
|
|||
}
|
||||
|
||||
.summary::after {
|
||||
content: "◀";
|
||||
content: "◀" / "";
|
||||
font-size: 1.2em;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
|
@ -822,7 +835,7 @@ details[open] .summary::after {
|
|||
}
|
||||
|
||||
.list-horizontal-text > *:not(:last-child)::after {
|
||||
content: '•';
|
||||
content: '•' / "";
|
||||
color: var(--color-text-subdue);
|
||||
margin: 0 0.4rem;
|
||||
position: relative;
|
||||
|
|
|
@ -4,17 +4,18 @@
|
|||
|
||||
{{ define "widget-content" }}
|
||||
<div class="widget-group-header">
|
||||
<div class="widget-header gap-20">
|
||||
{{ range $i, $widget := .Widgets }}
|
||||
<button class="widget-group-title{{ if eq $i 0 }} widget-group-title-current{{ end }}"{{ if ne "" .TitleURL }} data-title-url="{{ .TitleURL }}"{{ end }}>{{ $widget.Title }}</button>
|
||||
{{ end }}
|
||||
<div class="widget-header gap-20" role="tablist">
|
||||
{{- range $i, $widget := .Widgets }}
|
||||
<button class="widget-group-title{{ if eq $i 0 }} widget-group-title-current{{ end }}"{{ if ne "" .TitleURL }} data-title-url="{{ .TitleURL }}"{{ end }} aria-selected="{{ if eq $i 0 }}true{{ else }}false{{ end }}" arial-level="2" role="tab" aria-controls="widget-{{ .GetID }}-tabpanel-{{ $i }}" id="widget-{{ .GetID }}-tab-{{ $i }}">{{ $widget.Title }}</button>
|
||||
{{- end }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="widget-group-contents">
|
||||
{{ range $i, $widget := .Widgets }}
|
||||
<div class="widget-group-content{{ if eq $i 0 }} widget-group-content-current{{ end }}">{{ .Render }}</div>
|
||||
{{ end }}
|
||||
{{- range $i, $widget := .Widgets }}
|
||||
<div class="widget-group-content{{ if eq $i 0 }} widget-group-content-current{{ end }}" id="widget-{{ .GetID }}-tabpanel-{{ $i }}" role="tabpanel" aria-labelledby="widget-{{ .GetID }}-tab-{{ $i }}" aria-hidden="{{ if eq $i 0 }}false{{ else }}true{{ end }}">
|
||||
{{- .Render -}}
|
||||
</div>
|
||||
{{- end }}
|
||||
</div>
|
||||
|
||||
{{ end }}
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
|
||||
{{ define "navigation-links" }}
|
||||
{{ range .App.Config.Pages }}
|
||||
<a href="{{ $.App.Config.Server.BaseURL }}/{{ .Slug }}" class="nav-item{{ if eq .Slug $.Page.Slug }} nav-item-current{{ end }}">{{ .Title }}</a>
|
||||
<a href="{{ $.App.Config.Server.BaseURL }}/{{ .Slug }}" class="nav-item{{ if eq .Slug $.Page.Slug }} nav-item-current{{ end }}"{{ if eq .Slug $.Page.Slug }} aria-current="page"{{ end }}>{{ .Title }}</a>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
|
||||
|
@ -35,10 +35,10 @@
|
|||
<div class="header-container content-bounds">
|
||||
<div class="header flex padding-inline-widget widget-content-frame">
|
||||
<!-- TODO: Replace G with actual logo, first need an actual logo -->
|
||||
<div class="logo">{{ if ne "" .App.Config.Branding.LogoURL }}<img src="{{ .App.Config.Branding.LogoURL }}" alt="">{{ else if ne "" .App.Config.Branding.LogoText }}{{ .App.Config.Branding.LogoText }}{{ else }}G{{ end }}</div>
|
||||
<div class="nav flex grow">
|
||||
<div class="logo" aria-hidden="true">{{ if ne "" .App.Config.Branding.LogoURL }}<img src="{{ .App.Config.Branding.LogoURL }}" alt="">{{ else if ne "" .App.Config.Branding.LogoText }}{{ .App.Config.Branding.LogoText }}{{ else }}G{{ end }}</div>
|
||||
<nav class="nav flex grow">
|
||||
{{ template "navigation-links" . }}
|
||||
</div>
|
||||
</nav>
|
||||
</div>
|
||||
</div>
|
||||
{{ end }}
|
||||
|
@ -57,17 +57,19 @@
|
|||
</div>
|
||||
|
||||
<div class="content-bounds grow">
|
||||
<div class="page" id="page">
|
||||
<main class="page" id="page" aria-live="polite" aria-busy="true">
|
||||
<h1 class="visually-hidden">{{ .Page.Title }}</h1>
|
||||
<div class="page-content" id="page-content"></div>
|
||||
<div class="page-loading-container">
|
||||
<!-- TODO: add a bigger/better loading indicator -->
|
||||
<div class="loading-icon"></div>
|
||||
<div class="visually-hidden">Loading</div>
|
||||
<div class="loading-icon" aria-hidden="true"></div>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
</div>
|
||||
|
||||
{{ if not .App.Config.Branding.HideFooter }}
|
||||
<div class="footer flex items-center flex-column">
|
||||
<footer class="footer flex items-center flex-column">
|
||||
{{ if eq "" .App.Config.Branding.CustomFooter }}
|
||||
<div>
|
||||
<a class="size-h3" href="https://github.com/glanceapp/glance" target="_blank" rel="noreferrer">Glance</a> {{ if ne "dev" .App.Version }}<a class="visited-indicator" title="Release notes" href="https://github.com/glanceapp/glance/releases/tag/{{ .App.Version }}" target="_blank" rel="noreferrer">{{ .App.Version }}</a>{{ else }}({{ .App.Version }}){{ end }}
|
||||
|
@ -75,7 +77,7 @@
|
|||
{{ else }}
|
||||
{{ .App.Config.Branding.CustomFooter }}
|
||||
{{ end }}
|
||||
</div>
|
||||
</footer>
|
||||
{{ end }}
|
||||
|
||||
<div class="mobile-navigation-offset"></div>
|
||||
|
|
|
@ -2,9 +2,9 @@
|
|||
{{- if not .HideHeader}}
|
||||
<div class="widget-header">
|
||||
{{- if ne "" .TitleURL }}
|
||||
<a href="{{ .TitleURL | safeURL }}" target="_blank" rel="noreferrer" class="uppercase">{{ .Title }}</a>
|
||||
<h2><a href="{{ .TitleURL | safeURL }}" target="_blank" rel="noreferrer" class="uppercase">{{ .Title }}</a></h2>
|
||||
{{- else }}
|
||||
<div class="uppercase">{{ .Title }}</div>
|
||||
<h2 class="uppercase">{{ .Title }}</h2>
|
||||
{{- end }}
|
||||
{{- if .IsWIP }}
|
||||
<div data-popover-type="html" data-popover-position="above">
|
||||
|
|
|
@ -121,13 +121,13 @@ type widget interface {
|
|||
// These need to be exported because they get called in templates
|
||||
Render() template.HTML
|
||||
GetType() string
|
||||
GetID() uint64
|
||||
|
||||
initialize() error
|
||||
requiresUpdate(*time.Time) bool
|
||||
setProviders(*widgetProviders)
|
||||
update(context.Context)
|
||||
setID(uint64)
|
||||
id() uint64
|
||||
handleRequest(w http.ResponseWriter, r *http.Request)
|
||||
setHideHeader(bool)
|
||||
}
|
||||
|
@ -184,7 +184,7 @@ func (w *widgetBase) update(ctx context.Context) {
|
|||
|
||||
}
|
||||
|
||||
func (w *widgetBase) id() uint64 {
|
||||
func (w *widgetBase) GetID() uint64 {
|
||||
return w.ID
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue