---
title: Addons
path: /v5/addons/
index: 13
---
Addons are external functions that control or create many different Tippy
instances, and can be tree-shaken away by bundlers.
### Event delegation
Event delegation allows you to let a common parent element handle the creation
of tippy instances for child elements.
This allows two things:
- It prevents the need to create new instances for new child elements appended
to the parent.
- It improves performance as the creation of the tippy instances is deferred
until they are triggered for the first time.
#### Usage
Your markup should have a structure like this example:
```html
```
Pass a `targets` argument to the `delegate()` addon function (the same type the
`tippy()` function can accept) which represents the parent element(s) that
should act as a delegate, and a `target` prop representing a CSS selector that
should match the child elements which should receive a tippy.
```js
import {delegate} from 'tippy.js';
delegate('#parent', {
target: '.child',
});
```
In the CDN (`iife`) version, it's available as `tippy.delegate()`
#### Return type
Because `delegate()` can create many different instances, it returns an opaque
value depending on the type supplied, just like `tippy()`.
```js
const delegateInstances = delegate('.parent', {
target: '.child',
}); // Instance[]
const delegateInstance = delegate(parentElement, {
target: '.child',
}); // Instance
```
#### Cleanup
By default, when you destroy a delegate instance, it also destroys any child
instances that may have been created by it. If you want to prevent this
behavior, pass `false` as an argument:
```js
const delegateInstance = delegate(parentElement, {
target: '.child',
});
// Prevents further creation and destroys any created child tippy instances
delegateInstance.destroy();
// Prevents further creation only
delegateInstance.destroy(false);
```
#### Polyfill
This addon uses `Element.prototype.closest()`, which is not supported in older
browsers. You will need to polyfill this method to get full support.
---
### Singleton
A singleton is a single tippy element that takes the place of an array of
regular tippy instances.
This allows two things:
- Smooth transitions of the tippy between many different reference element
targets
- Elements with tooltips next to each other that have a `delay` can be "grouped"
so they appear to share a timeout, which greatly improves UX
See the [demo](/#singleton) for it in action.
#### Usage
Pass an **array** of tippy instances to the `createSingleton` addon function,
and a `delay` prop:
```js
import tippy, {createSingleton} from 'tippy.js';
const tippyInstances = tippy('button');
const singleton = createSingleton(tippyInstances, {delay: 1000});
```
In the CDN (`iife`) version, it's available as `tippy.createSingleton()`
#### Smooth transitions
Utilize the `updateDuration` prop, which is the transition duration between
position updates of the tippy element:
```js
const singleton = createSingleton(tippyInstances, {
delay: 1000,
updateDuration: 500,
});
```
> **Note**
>
> Enabling transitions may cause overflow issues if the tippy content is near
> the right/bottom edge of a boundary (e.g. window) and the tippy content
> changes from small to large. This is because of the transition causing the
> tippy to expand the boundary, making Popper.js think it will fit.
To solve this, constrain the tippy to the viewport:
```js
createSingleton(instances, {
boundary: 'viewport',
});
```
#### Timing function
The `transition-timing-function` by default is `easeOutQuint`. Usually this
looks nice, but you can change this (to add an inertial slingshot effect for
example) like so:
```js
const singleton = createSingleton(tippyInstances, {
updateDuration: 500,
onCreate({popper}) {
// Any easing function you want.
popper.style.transitionTimingFunction = 'cubic-bezier(...)';
},
});
```