High-level web components built from the elements library for interfaces, interactivity, layout, and data feeds. This library provides ready-to-use web components that follow the University of Maryland's design guidelines and accessibility standards. These components are designed to work seamlessly together to create consistent, branded UMD web experiences while maintaining performance and usability across all devices.
# Using npm
npm install @universityofmaryland/web-components-library
# Using yarn
yarn add @universityofmaryland/web-components-library
The simplest way to use the components is to load all of them at once. This approach is ideal for applications that use many UMD components.
import LoadUmdComponents from '@universityofmaryland/web-components-library';
document.addEventListener('DOMContentLoaded', () => {
LoadUmdComponents();
// All components are now registered and available in the DOM
});
For better performance, you can import only the components you need:
import {
card,
navigation,
hero,
} from '@universityofmaryland/web-components-library/Components';
// Initialize specific components
card.standard();
navigation.header();
hero.minimal();
The library includes a wide range of components organized by type:
layout.boxLogo
- Box with logo layoutlayout.imageExpand
- Expandable image layoutlayout.modal
- Modal dialoglayout.scrollTop
- Scroll to top buttonlayout.stickyColumns
- Sticky columns layoutaccordion
- Collapsible content panelsactions
- Action buttons and linksalert
- Alert notificationscard
- Various card styles (standard, article, overlay)carousel
- Image and content carouselshero
- Hero sections (standard, minimal, expand, logo)navigation
- Navigation components (header, drawer, breadcrumb)person
- Person/profile componentsquote
- Quote/testimonial componentsstat
- Statistics displaytab
- Tabbed interfacetext
- Text components<umd-element-card>
<img slot="image" src="path/to/image.jpg" alt="Card image" />
<p slot="eyebrow">Category</p>
<h3 slot="headline">Card Title</h3>
<p slot="text">
Card description text goes here with details about the card content.
</p>
<div slot="actions">
<a href="#">Learn More</a>
</div>
</umd-element-card>
The library uses a sophisticated model system for creating and registering web components with consistent behavior, validation, and lifecycle management.
Components are registered using the Register.webComponent()
utility:
import { Register } from 'model';
export default Register.webComponent({
tagName: 'umd-element-example',
slots: slotConfiguration,
createComponent: componentFactory,
attributes: attributeHandlers, // Optional: reactive attribute observers
afterConnect: lifecycleCallback, // Optional: lifecycle hooks
});
The library uses two types of attributes:
Set initial component state and configuration:
<umd-element-card data-theme="dark">
<!-- Content -->
</umd-element-card>
Common configuration attributes:
data-theme
- Color theme (light
, dark
)data-display
- Display style (grid
, list
, inline
)data-visual-open
- Initial open statedata-size
- Component size (small
, medium
, large
)Trigger component behavior when changed:
// Programmatic control
element.setAttribute('is-visual-open', 'true');
element.setAttribute('resize', 'true');
Common observed attributes:
is-visual-open
- Opens componentis-visual-closed
- Closes componentresize
- Triggers resize calculationload
- Triggers load eventThe library provides pre-built attribute handlers:
import { Attributes } from 'model';
// Single handler
const resizeHandler = Attributes.handler.common.resize();
// Combined handlers
const multiHandler = Attributes.handler.combine([
Attributes.handler.common.resize(),
Attributes.handler.common.visualToggle(),
]);
// Custom handler with callback
const customHandler = Attributes.handler.common.resize((element) => {
element.events?.recalculate();
});
Available handlers:
resize()
- Handles component resizingvisualToggle()
- Open/close animationsvisualShowHide()
- Show/hide visibilityaccordion()
- Complete accordion behaviorComponents use a slot-based content distribution system with validation:
import { Slots } from 'model';
const slots = {
headline: {
allowedElements: ['h1', 'h2', 'h3', 'h4', 'h5', 'h6'],
required: true,
},
text: {
allowedElements: ['div', 'p'],
required: false,
},
actions: {
allowedElements: ['div', 'nav'],
deprecated: { replacement: 'cta' },
},
};
Using slots in HTML:
<umd-element-example>
<h3 slot="headline">Title</h3>
<p slot="text">Content text</p>
<div slot="actions">
<a href="#">Learn More</a>
</div>
</umd-element-example>
Pre-built lifecycle hooks for common initialization patterns:
import { Lifecycle } from 'model';
// Available hooks
afterConnect: Lifecycle.hooks.loadOnConnect, // Calls load event
afterConnect: Lifecycle.hooks.loadAnimation, // Sets up animations
afterConnect: Lifecycle.hooks.resizeOnConnect, // Triggers resize
Example of a complete component implementation:
import { Composite } from '@universityofmaryland/web-elements-library';
import { Attributes, Slots, Register, Lifecycle } from 'model';
import type { CreateComponentFunction, SlotConfiguration } from '../_types';
// Define the custom element tag name
const tagName = 'umd-custom-component';
// Configure slots with validation
const slots: SlotConfiguration = {
headline: {
allowedElements: ['h2', 'h3', 'h4'],
required: true,
},
text: {
allowedElements: ['p', 'div'],
},
image: {
allowedElements: ['img', 'picture'],
required: false,
},
};
// Create the component factory function
const createComponent: CreateComponentFunction = (element) => {
// Extract validated slot content
const headline = Slots.headline.default({ element });
const text = Slots.text.default({ element });
const image = Slots.query.elements({ element, name: 'image' });
// Extract configuration attributes
const isThemeDark = Attributes.isTheme.dark({ element });
const displayStyle = element.getAttribute('data-display') || 'default';
// Create component using the Elements library
return Composite.customComponent.create({
headline,
text,
image,
isThemeDark,
displayStyle,
});
};
// Register the web component with all features
export default Register.webComponent({
tagName,
slots,
createComponent,
attributes: [
Attributes.handler.common.resize(),
Attributes.handler.common.visualToggle(),
],
afterConnect: Lifecycle.hooks.loadOnConnect,
});
Components dispatch custom events for state changes:
// Listen for component events
element.addEventListener('component:ready', (e) => {
console.log('Component initialized');
});
element.addEventListener('component:resize', (e) => {
console.log('Component resized');
});
element.addEventListener('component:error', (e) => {
console.error('Component error:', e.detail);
});
Components automatically update when observed attributes change:
// Triggers resize handler
element.setAttribute('resize', 'true');
// Triggers visual state change
element.setAttribute('is-visual-open', 'true');
All components use Shadow DOM for style encapsulation:
// Access shadow root
const shadowRoot = element.shadowRoot;
// Query within shadow DOM
const internalElement = shadowRoot.querySelector('.component-part');
# Clone the repository
git clone https://github.com/umd-digital/design-system.git
cd design-system/packages/components
# Install dependencies
npm install
# Start development server
npm start
# Production build
npm run build
# Build and publish to npm
npm run release
The library uses Jest with jsdom for testing web components:
# Run all tests
npm test
# Run tests in watch mode
npm run test:watch
# Generate coverage report
npm run test:coverage
# Run specific test file
npm test -- source/api/__tests__/card/standard.test.ts
Each component test validates:
customElements
The library is built with TypeScript and provides comprehensive type definitions:
import type {
ComponentRef,
CreateComponentFunction,
ComponentRegistration,
SlotConfiguration,
ThemeProps,
VisualStateProps,
ComponentEvents,
} from '@universityofmaryland/web-components-library';
Key interfaces:
ComponentRef
- Reference returned by component factoriesSlotConfiguration
- Slot validation rulesCreateComponentFunction
- Component factory signatureComponentRegistration
- Registration function typeAttributeHandler
- Attribute observer configurationimport { CommonSlots } from 'model/slots/common';
const slots = {
headline: CommonSlots.headline, // Pre-configured headline slot
text: CommonSlots.text, // Pre-configured text slot
actions: CommonSlots.actions, // Pre-configured actions slot
customSlot: {
// Custom slot definition
allowedElements: ['div', 'section'],
required: false,
},
};
Components can be composed from other components:
import {
card,
hero,
} from '@universityofmaryland/web-components-library/Components';
// Initialize multiple components
card.standard();
card.overlay();
hero.minimal();
// Components work together
const heroWithCards = `
<umd-element-hero>
<h1 slot="headline">Welcome</h1>
<div slot="actions">
<umd-element-call-to-action>
<!-- CTA Slot Options -->
</umd-element-call-to-action>
</div>
</umd-element-hero>
`;
The UMD Web Components Library supports all modern browsers that support Web Components, including:
For older browsers, consider using the Web Components polyfills.
This library depends on:
@universityofmaryland/web-elements-library
(^1.2.0) - For foundational UI elements@universityofmaryland/web-styles-library
(^1.4.2) - For styling and themingAll components in this library are designed with accessibility in mind:
prefers-reduced-motion
For contribution guidelines, please refer to the main repository README.
This project is licensed under the University of Maryland license.