Skip to content

A semantic, accessible WordPress glossary plugin that automatically links terms to hover-triggered popover definitions.

License

Notifications You must be signed in to change notification settings

ProgressPlanner/pp-glossary

Glossary by Progress Planner

Try Glossary on the WordPress playground

Glossary

A semantic, accessible WordPress glossary plugin that automatically links terms to click-triggered popover definitions using native WordPress functionality.

Features

  • Custom Post Type: Register glossary entries with custom fields (no content editor needed)
  • Native WordPress Fields: Uses WordPress custom meta boxes for field management (short description, long description, synonyms)
  • Automatic Term Linking: Automatically transforms the first mention of glossary terms in your content
  • Click-Triggered Popovers: Display definitions on click using the native Popover API with CSS Anchor Positioning
  • Case Sensitive Matching: Optionally match terms only when case matches exactly
  • Disable Auto-Linking: Allow entries to appear in the glossary without being automatically linked in content
  • Semantic HTML: Uses <dfn> and <aside> elements with proper ARIA attributes
  • Schema.org Integration: Full DefinedTerm and DefinedTermSet structured data support
    • Integrates with Yoast SEO schema graph when available
    • Falls back to Microdata when Yoast SEO is not active
  • Synonyms Support: Define alternative terms that trigger the same glossary entry
  • Glossary Block: Gutenberg block to display full glossary with alphabetical navigation
  • Settings Page: Configure which page displays the glossary
  • Accessible: Full keyboard navigation and screen reader compatibility
  • Responsive Design: Mobile-friendly with CSS custom properties for easy theming
  • No External Dependencies: Pure WordPress core functionality, no third-party plugins required

Requirements

  • WordPress 6.0 or higher
  • PHP 7.4 or higher
  • Modern browser with Popover API support (Chrome 114+, Edge 114+, Safari 17+)

Installation

  1. Download or clone this repository into your WordPress plugins directory:

    cd wp-content/plugins/
    git clone [repository-url] pp-glossary
  2. Activate the "Glossary by Progress Planner" plugin in your WordPress admin panel

  3. Navigate to Glossary in the WordPress admin menu to start adding entries

Setup

1. Create a Glossary Page

  1. Create a new page in WordPress (e.g., "Glossary" or "Terms")
  2. Add the Glossary List block to the page
  3. Configure the block settings (show/hide title, custom title text)
  4. Publish the page

2. Configure Settings

  1. Go to Glossary > Settings in the WordPress admin
  2. Select the page you created as the "Glossary Page"
  3. Save settings

3. Add Glossary Entries

  1. Go to Glossary > Add New
  2. Enter the term as the title (e.g., "Cumulative Layout Shift")
  3. Fill in the custom fields in the "Glossary Entry Details" meta box:
    • Short Description (required): Brief definition (1-2 sentences) shown in popovers
    • Long Description: Detailed explanation shown on the glossary page
    • Synonyms: Alternative terms (e.g., "CLS", "layout shift") - click "Add Synonym" to add more
    • Case Sensitive: Enable to only match terms when the case matches exactly
    • Disable Auto-Linking: Enable to prevent this entry from being automatically linked in content
  4. Publish the entry

Usage

Automatic Term Linking

Once you've added glossary entries, the plugin automatically:

  • Scans post and page content for mentions of glossary terms (case-insensitive by default, or case-sensitive if enabled)
  • Transforms the first mention of each term into an interactive element (unless auto-linking is disabled for that entry)
  • Shows a popover with the short description when users click on the term
  • Adds a "Read more" link to the full glossary entry

The Glossary Block

The Glossary List block displays:

  • Optional title
  • Alphabetical navigation (A-Z)
  • All entries grouped by first letter
  • Short and long descriptions for each entry
  • Synonym listings

Click Behavior

  • Mouse users: Click on a dotted underlined term to see the definition
  • Keyboard users: Tab to the term and press Enter or Space to open the popover
  • Touch users: Tap the term to toggle the popover
  • Press Escape or click elsewhere to close the popover

HTML Structure

The plugin generates semantic, accessible HTML with CSS Anchor Positioning:

<!-- Glossary term with anchor definition -->
<dfn id="dfn-term-1"
     class="pp-glossary-term"
     style="anchor-name: --dfn-term-1;">
  <button data-glossary-popover="pop-term-1"
          type="button"
          aria-expanded="false">
    term
  </button>
</dfn>

<!-- Popover anchored to the term -->
<aside id="pop-term-1"
       popover="auto"
       role="tooltip"
       aria-labelledby="dfn-term-1"
       style="position-anchor: --dfn-term-1;">
  <p><a href="/glossary/#term-slug">Read more about <strong>Term</strong></a></p>
  <p>Short description of the term.</p>
</aside>

The glossary block itself includes Schema.org structured data (Microdata when Yoast SEO is not active, JSON-LD when Yoast SEO is active):

<!-- Glossary block with schema markup -->
<div class="pp-glossary-block"
     itemscope
     itemtype="https://schema.org/DefinedTermSet"
     itemid="https://example.com/glossary/#glossary">

  <meta itemprop="name" content="Glossary">

  <!-- Each entry -->
  <article id="term-slug"
           class="glossary-entry"
           itemprop="hasDefinedTerm"
           itemscope
           itemtype="https://schema.org/DefinedTerm">

    <link itemprop="url" href="https://example.com/glossary/#term-slug">

    <h4 class="glossary-entry-title" itemprop="name">Term Title</h4>

    <div class="glossary-synonyms">
      <span class="synonyms-label">Also known as:</span>
      <span>Synonym 1, Synonym 2</span>
      <meta itemprop="alternateName" content="Synonym 1">
      <meta itemprop="alternateName" content="Synonym 2">
    </div>

    <div class="glossary-long-description" itemprop="description">
      Long description of the term...
    </div>
  </article>
</div>

Note: When Yoast SEO is active, the Microdata attributes are omitted and structured data is added to Yoast's JSON-LD schema graph instead.

Customization

Styling

The plugin uses CSS custom properties for easy theming, with their defaults listed:

:root {
  --glossary-underline-color: rgba(0, 0, 0, 0.4);
  --glossary-underline-hover-color: rgba(0, 0, 0, 0.7);
  --glossary-focus-color: #005a87;
  --glossary-bg-color: #fff;
  --glossary-border-color: #ddd;
  --glossary-text-color: #333;
  --glossary-heading-color: #000;
  --glossary-link-color: #0073aa;
  --glossary-accent-color: #0073aa;
  --glossary-nav-bg: #fff;
  --glossary-letter-bg: #f5f5f5;
  --glossary-letter-color: #333;
  --glossary-letter-hover-bg: #0073aa;
  --glossary-letter-hover-color: #fff;
  --glossary-entry-bg: #f9f9f9;
  --glossary-meta-color: #666;
}

Filters

Modify behavior using WordPress filters:

// Disable content filtering for specific post types.
add_filter( 'pp_glossary_disabled_post_types', function( $post_types ) {
    // Disable filtering for 'product' and 'custom_post_type'.
    return array( 'product', 'custom_post_type' );
} );

Browser Support

The plugin uses modern web platform features:

Popover API:

  • Chrome/Edge 114+
  • Safari 17+
  • Firefox (experimental support behind flag)

CSS Anchor Positioning:

  • Chrome/Edge 125+/Safari: supported
  • Firefox (not yet supported)

For older browsers:

  • Consider adding the Popover API polyfill
  • CSS Anchor Positioning gracefully degrades (popovers may not position optimally but will still be functional)

Schema.org Structured Data

The plugin automatically adds Schema.org structured data for glossary entries:

With Yoast SEO

When Yoast SEO is active, the plugin integrates with the Yoast schema graph API to add:

  • DefinedTermSet for the glossary page
  • DefinedTerm for each glossary entry

The structured data appears in Yoast's JSON-LD output and is compatible with Yoast's schema features.

Without Yoast SEO

When Yoast SEO is not active, the plugin outputs Microdata markup directly in the HTML:

  • Uses itemscope and itemtype attributes on the glossary block
  • Each entry includes proper itemprop attributes for name, description, URL, and synonyms
  • Fully compliant with Schema.org DefinedTerm specification

Schema Properties

Each glossary entry includes:

  • @type: DefinedTerm
  • name: The term title
  • description: Short description (shown in popovers)
  • url: Anchor link to the entry on the glossary page
  • alternateName: Array of synonyms (alternative terms)

Accessibility

The plugin follows WCAG 2.1 Level AA guidelines:

  • Semantic HTML elements (<dfn>, <aside>, proper roles)
  • Full keyboard navigation with visible focus indicators
  • ARIA attributes for screen readers
  • Click-to-open behavior (not hover) for better accessibility
  • Auto-dismissing popovers that don't overlap
  • Color contrast ratios meet AA standards

Development

No Build Process

The plugin uses vanilla JavaScript and CSS - no build process required!

Coding Standards

Follows WordPress Coding Standards:

To check code:

composer install
composer run phpcs

License

GPL v2 or later

Changelog

1.2.0

  • Excluded glossary entries from Yoast SEO indexables and XML sitemaps (entries have no public pages)
  • Excluded glossary entries from WordPress search results
  • Removed revision support (all data is in post meta, not tracked by revisions)
  • Added a setting to configure excluded HTML tags where glossary terms should not be highlighted
  • Added a setting to exclude specific post types from glossary term highlighting

1.1.0

  • Added case sensitive option for glossary entries - only matches terms when case matches exactly
  • Added disable auto-linking option - allows entries to appear in the glossary without being automatically linked in content
  • Consolidated glossary entry meta data into a single database post meta field for improved performance
  • Added automatic migration system for seamless upgrades
  • Glossary block improvements:
    • Now falls back to short description when long description is empty
    • Now shows an edit link for logged in users per glossary item
  • Accessibility fixes:
    • Popover now opens on click, not on hover, and no longer auto-closes
    • Removed redundant aria-describedby attribute
    • Link appears inside the popover before the definition for better screen reader context
    • Popovers are now type auto instead of manual so they dismiss other popovers and don't overlap

1.0.3

  • Fix non-bumped version number

1.0.2

  • Asset fixes

1.0.1

  • Minor bug fixes

1.0.0

  • Initial release
  • Custom post type for glossary entries
  • Native WordPress custom fields (short description, long description, synonyms)
  • Hover-triggered popovers using Popover API with CSS Anchor Positioning
  • Automatic term linking (first occurrence only)
  • Glossary List Gutenberg block
  • Settings page for glossary page configuration
  • Schema.org structured data (DefinedTerm and DefinedTermSet)
    • Yoast SEO integration (JSON-LD)
    • Microdata fallback when Yoast is not active
  • Semantic, accessible HTML
  • Responsive design with CSS custom properties
  • Full keyboard and screen reader support
  • No external plugin dependencies

About

A semantic, accessible WordPress glossary plugin that automatically links terms to hover-triggered popover definitions.

Resources

License

Code of conduct

Contributing

Security policy

Stars

Watchers

Forks

Packages

No packages published

Contributors 5