Volue logo
Volue logomark
Wave Core
Show Hide
v1.14.1 16-10-2024
Jump to section

Breakpoint manager

Utility to observe changes in breakpoints and adapt UI accordingly

Breakpoints are the defined thresholds at which the layout (and modules) will adjust to fit the size of a device or browser window. Breakpoints are specified in the CSS using media queries. The media queries set different rules for each breakpoint so the UI can be adapted appropriately.

This utility allows you to add JavaScript callbacks for Wave's media queries matching. Being able to run JavaScript based on the breakpoint can be quite useful for unifying responsive presentation and behavior.

Breakpoint manager is built without using matchMedia, which makes it compatable with IE9.

Options

var bpManager = Wave.BreakpointManager({
  debounceTime: 200 // duration of debounce set on the window#resize or orientationchange events (default is 250)
});

Utility's API

.start() starts listening to window#resize or orientationchange events and fires events when the browser enters declared breakpoints.

.stop() stops listening to window#resize or orientationchange events and disables event firing.

.getAll() returns an array of all the available breakpoints.

.getCurrent() returns the active breakpoint.

.on('change' function(breakpoint)) generic event that triggers whenever the breakpoint changes and returns the new breakpoint's name to your callback function.

.on('medium', function()) event that triggers each time a specific breakpoint threshold is crossed.

List of breakpoints

small
screen and ( max-width: 31.1875em )
medium
screen and ( min-width: 31.25em )
large
screen and ( min-width: 48.75em )
xlarge
screen and ( min-width: 87.5em )

* 1em equals 16px

You can add a badge to the bottom left of the body to show the current breakpoint. To enable this, add .dev-showBreakpoint class to the HTML element.

Usage example

var bpManager = Wave.BreakpointManager();
bpManager.start();

bpManager.on('change', function (bp) {
  console.log('[Wave.BreakpointManager] breakpoint changed: ' + bp + '!');
});

bpManager.on('medium', function () {
  console.log('[Wave.BreakpointManager] entered medium breakpoint');
});

document.addEventListener("DOMContentLoaded", function() {
  console.log('[Wave.BreakpointManager] available breakpoints: ' + JSON.stringify(bpManager.getAll(), null, 4));
});

See console log for the output.


Viewport monitor

Utility that represents the browsers viewport in a more useful way

Viewport monitor attaches listeners to resize and scroll events and lets you observe changes in the viewport. It uses requestAnimationFrame for performance.

var viewportMonitor = Wave.ViewportMonitor();

Utility's API

.width current width of the viewport (in pixels).

.height current height of the viewport (in pixels).

.top current top offset of the viewport.

.right current right offset of the viewport.

.bottom current bottom offset of the viewport.

.right current left offset of the viewport.

.scrollY current vertical scroll position of viewport.

.scrollX current horizontal scroll position of viewport.

.scrollDirection current scroll direction (1 if the scroll goes forward or -1 if the scroll goes backward).

.orientation current orientation of the viewport (landscape or portrait).

.isScrollMax() determines if scroll position is at maximum for the document.

.isScrollMin() determines if scroll position is at minimum for the document.

.isInViewport(element, verge) determines if a given element is in the viewport. The optional verge parameter is an amount of pixels to act as a cushion around the viewport. Returns boolean.

.isInY(element, verge) determines if a given element is in the same y-axis section as the viewport. Returns boolean.

.isInX(element, verge) determines if a given element is in the same x-axis section as the viewport. Returns boolean.

.mq(mediaQueryString) determines if a given media query is active using matchMedia (https://caniuse.com/#feat=matchmedia). Returns boolean.

.on('scroll', function()) event that triggers when the viewport is scrolled.

.on('resize', function()) event that triggers when the dimensions of the viewport changes.

Usage example

var viewportMonitor = Wave.ViewportMonitor(),
  testElement = document.querySelector('.js-testElement'),
  isTestElementInViewport = function () {
    if (viewportMonitor.isInViewport(testElement, 50)) {
      console.log('[Wave.ViewportMonitor] test element is in the viewport');
    } else {
      console.log('[Wave.ViewportMonitor] test element is outside of the viewport');
    }
  };

console.log('[Wave.ViewportMonitor] Dimensions: %s x %s',
  viewportMonitor.width,
  viewportMonitor.height
);

if (viewportMonitor.mq('(hover)')) {
  console.log('[Wave.ViewportMonitor] has hover capability');
}

viewportMonitor.on('scroll', function () {
  console.log('[Wave.ViewportMonitor] scrolling. ScrollY: %s, ScrollX: %s, ScrollDirection: %s',
    this.scrollY,
    this.scrollX,
    this.scrollDirection
  );
  if (this.isScrollMin()) {
    console.log('[Wave.ViewportMonitor] scroll position is at minimum for the document');
  }
  if (this.isScrollMax()) {
    console.log('[Wave.ViewportMonitor] scroll position is at maximum for the document');
  }
  isTestElementInViewport();
});

viewportMonitor.on('resize', function () {
  console.log('[Wave.ViewportMonitor] resizing. Width: %s, Height: %s, Orientation: %s',
    this.width,
    this.height,
    this.orientation
  );
  isTestElementInViewport();
});

Open your console and start to scroll and resize the viewport to see the output.

test element

Debounce

Useful utility to limit the rate at which a function can fire

var debouncedResizeHandler = Wave.utils.debounce(function () {
  console.log('250 ms after the end of a window resizing action');
}, 250);

window.addEventListener('resize', debouncedResizeHandler);

var debouncedKeyUpHandler = Wave.utils.debounce(function () {
  console.log('250 ms after the last keyup');
}, 250);

input.addEventListener('keyup', debouncedKeyUpHandler)

Debouncing will fire your function after a threshold of time (e.g. quarter of a second) has elapsed since the last time it’s tried to fire. Debouncing resize event handler makes a huge performance difference.

Another good use case for this is if you want to wait until a user has stopped scrolling or typing in an input field to trigger some action.


Throttle per frame

Utility that lets you create a throttled function, which only invokes the passed function at most once per animation frame

var someEl = document.querySelector('.someEl');

var throttledScrollHandler = Wave.utils.rafThrottle(function (event) {
  if (someEl.offsetTop <= window.pageYOffset) {
    someEl.style.position = 'fixed';
  } else {
    someEl.style.position = 'static';
  }

  console.log('this should trigger once per animation frame');
});

window.addEventListener('scroll', throttledScrollHandler);

The main difference between this and debouncing is that throttle guarantees the execution of your function regularly. If called multiple times within a single animation frame, it will be triggered once in the current frame, and once on the next frame.

Use it at everything that involves re-calculating sizes and positions.


Features

Utility to test if the environment we are in is capable of using certain feature

Wave.utils.hasFeature('svg'); // returns boolean (true or false), indicating whether SVG is supported
Wave.utils.hasFeature('touch'); // returns boolean, indicating whether touch events are supported
Wave.utils.hasFeature('orientationChange'); // returns boolean, indicating whether the native orientationchange event is supported

Wave.utils.featureTests will return an array containing all available tests.


Style support check

Utility to detect support for both CSS styles and their assignable values

Provide a style property as the first argument. Second argument to determine support for the style's value is optional.

You are not required to provide vendor prefixes for properties (that is done internally), but property values may require a vendor prefix depending on the value you wish to test.

Wave.utils.isStyleSupported('animation-name'); // returns boolean (true or false), indicating whether CSS animations are supported
Wave.utils.isStyleSupported('transition-property'); // returns boolean (true or false), indicating whether CSS transitions are supported
Wave.utils.isStyleSupported('display', 'flex'); // returns boolean, indicating whether flexbox standard syntax is supported
Wave.utils.isStyleSupported('display', '-webkit-flex'); // returns boolean, indicating whether webkit-prefixed flexbox syntax is supported

Scrollbar size

Utility for calculating scrollbar size cross-browser

Wave.utils.getScrollbarSize(); // returns integer value

Smooth scroll

Utility that enables smooth scrolling

Wave.utils.smoothScroll(
  element,        // a DOM node or Window object
  { top: 400 },   // destination of the scroll (an object with top and left properties)
  1000,           // time of the scroll in milliseconds (default is 300)
  function () {}  // optional callback function to run at the end of scrolling
);

Usage example

$(document.querySelector('.js-smoothScroll')).on('click', function (e) {
  e.preventDefault();

  var sections = document.querySelectorAll('.section'),
    randSection = sections[Math.floor(Math.random() * sections.length)],
    destination = randSection.getBoundingClientRect().top + (window.pageYOffset || document.documentElement.scrollTop);

  Wave.utils.smoothScroll(window, { top: destination }, 500);
});

Load SVG

Utility for ajaxing for SVG files

Useful for loading an SVG sprite with icons over XHR and injecting it onto the page.

Wave.utils.loadSvg('svg/sprite.svg', function (err, svg) {
  document.body.insertBefore(svg, document.body.childNodes[0]);
});

Load CSS

Utility for loading CSS files asynchronously

Loads CSS file by dynamically injecting a <link> element into the <head> of the document. Stylesheet is loaded in a non-blocking manner, letting the document render while it is fetched. Only non-critical CSS files should be deferred to load asynchronously.

Wave.utils.loadCss(
  'css/style.css',
  { prepend: true }, // optionally prepend the link element to the head (defaults to append)
  function () { // optional callback function
    console.log('css has been loaded');
  }
});

Mobile check

Utility for detecting mobile devices

It uses the user-agent string to detect mobile devices.

Use carefully as device sniffing isn't condidered best practice. Resort to device detection only if feature tests/detection is impossible or in edge cases such as performance.

Wave.utils.isMobile(); // returns boolean (true or false), indicating whether the device is mobile
Announcement

This is the technical documentation of Wave Core library, the foundational part of Wave Design System.

Currently we are working on brand new design system site and a set of polished React components that aim to work out of the box, be accessible and deliver superior developer and user experience. Browse the new Wave Design System site and Wave React components docs at https://wave.volue.com.