Clipboard
Copy text from a source element to the clipboard on button click, with optional brief feedback.
Usage
Copy clipboard_controller.js to app/javascript/controllers/ and register it:
// app/javascript/controllers/index.js
import ClipboardController from "./clipboard_controller";
application.register("clipboard", ClipboardController);
HTML
<!-- Copy an input's value -->
<div data-controller="clipboard">
<input
type="text"
value="Hello world"
data-clipboard-target="source"
readonly
/>
<button type="button" data-action="click->clipboard#copy">Copy</button>
<span data-clipboard-target="feedback" hidden aria-live="polite"
>Copied!</span
>
</div>
<!-- Copy text content from any element -->
<div data-controller="clipboard">
<code data-clipboard-target="source">gem "stimulus-rails"</code>
<button type="button" data-action="click->clipboard#copy">Copy</button>
</div>
<!-- Custom feedback duration (500ms) -->
<div data-controller="clipboard" data-clipboard-success-duration-value="500">
<input type="text" value="API key" data-clipboard-target="source" readonly />
<button type="button" data-action="click->clipboard#copy">Copy</button>
<span data-clipboard-target="feedback" hidden aria-live="polite"
>Copied!</span
>
</div>
API
Targets
| Target | Required | Description |
|---|
source | Yes | Element to copy from. Uses .value if present (input/textarea), otherwise .textContent. |
feedback | No | Element shown briefly after a successful copy. |
Values
| Value | Type | Default | Description |
|---|
successDuration | Number | 2000 | Milliseconds to show the feedback target. |
Actions
| Action | Description |
|---|
copy | Copies source text to clipboard |
Accessibility
- Add
aria-live="polite" to the feedback element (already shown in the example) so screen readers announce the confirmation.
- Uses the
navigator.clipboard API, which requires a secure context (HTTPS or localhost) and may prompt for permission in some browsers.