# makeup-expander

Creates the basic interactivity for an element that expands and collapses another element.

## Experimental

This module is still in an experimental state, until it reaches v1 you must consider all minor releases as breaking changes.

## Example 1: Uses aria-expanded

In the first example, our expanded content is adjacent to the host element.

```html
<div class="expander">
  <button class="expander__host">Click for Popover</button>
  <div class="expander__content">
    <p>Any kind of HTML control can go inside...</p>
    <p>A link: <a id="foo" href="http://www.ebay.com">www.ebay.com</a></p>
    <p>A button: <button>Click Me</button></p>
    <p>An input: <input type="text" aria-label="Dummy textbox" /></p>
    <p>A checkbox: <input type="checkbox" aria-label="Dummy checkbox" /></p>
  </div>
</div>
```

```js
import Expander from "makeup-expander";

// get an element reference
const widgetEl = document.querySelector(".expander");

// options
const options = {
  expandOnClick: true,
};

// get widget instance
const widget = new Expander(widgetEl, options);
```

Clicking the button will now toggle its expanded state (setting aria-expanded on the element, by default). CSS can be used to display the content accordingly, for example:

```css
.expander__content {
  display: none;
}

.expander__host[aria-expanded="true"] ~ .expander__content {
  display: block;
}
```

## Example 2: Uses a class

In this second example, we use a class. This can be useful when our expanded content is not adjacent to the host element or when aria-expanded is not required.

```html
<div class="expander">
  <span>
    <input class="expander__host" type="text" />
  </span>
  <div class="expander__content">
    <p>Any kind of HTML control can go inside...</p>
    <p>A link: <a id="foo" href="http://www.ebay.com">www.ebay.com</a></p>
    <p>A button: <button>Click Me</button></p>
    <p>An input: <input type="text" aria-label="Dummy textbox" /></p>
    <p>A checkbox: <input type="checkbox" aria-label="Dummy checkbox" /></p>
  </div>
</div>
```

A CSS classname is required as our styling hook. This can be passed in via the options.

```js
// options
const options = {
  expandedClass: "expander--expanded",
  expandOnFocus: true,
};
```

Setting focus on the host adds the chosen class to the root. CSS can be used to display the content accordingly, for example:

```css
.expander--expanded .expander__content {
  display: block;
}
```

## Params

- `el`: the root widget el
- `options.alwaysDoFocusManagement`: whether `focusManagement` option (see below) should apply for mouse click
- `options.ariaControls`: specify whether `aria-controls` relationship should be created between host and overlay (default: true)
- `options.autoCollapse`: applies a collapse behavior (`collapseOnClick`, `collapseOnFocusOut`, `collapseOnMouseOut`) based on expand behaviour (default: false)
- `options.collapseOnClickOut`: whether the content should collapse when clicking outside of content (default: false)
- `options.collapseOnFocusOut`: whether the content should collapse when focus leaves the content (default: false)
- `options.collapseOnMouseOut`: whether the content should collapse when mouse leaves the content (default: false)
- `options.collapseOnHostReFocus`: whether the content should collapse when focus moves back to the host from content (default: false). This cannot be set to true when expandOnFocus is true
- `options.contentSelector`: the query selector for the expandee element in relation to the widget (default: '.expander\_\_content')
- `options.expandOnClick`: whether the host should be click activated (default: false)
- `options.expandOnFocus`: whether the host should be focus activated (default: false)
- `options.expandOnHover`: whether the host should be hover activated (default: false)
- `options.focusManagement`: where keyboard focus should go (null, 'content', 'focusable', 'interactive', or ID reference) when expanded via `ENTER` or `SPACEBAR` (default: null)
- `options.hostSelector`: the query selector for the host element in relation to the widget (default: '.expander\_\_host')
- `options.expandedClass`: the class which will be used on the root element to signify expanded state.
- `options.useAriaExpanded`: set to false for tooltips (default: true)

## Properties

Set the following properties to true or false to enable or disable the behaviour.

- `collapseOnClickOut`
- `collapseOnFocusOut`
- `collapseOnMouseOut`
- `expanded`
- `expandOnClick`
- `expandOnFocus`
- `expandOnHover`

## Events

- `expander-collapse`
- `expander-expand`
