PHPackages                             braesident/dropdown - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Utility &amp; Helpers](/categories/utility)
4. /
5. braesident/dropdown

ActiveExtension[Utility &amp; Helpers](/categories/utility)

braesident/dropdown
===================

Dropdown for Bootstrap

1.0.6(2mo ago)021proprietaryJavaScript

Since Sep 21Pushed 2mo agoCompare

[ Source](https://github.com/braesident/Dropdown)[ Packagist](https://packagist.org/packages/braesident/dropdown)[ Docs](https://www.exunova.de)[ RSS](/packages/braesident-dropdown/feed)WikiDiscussions master Synced 1mo ago

READMEChangelogDependenciesVersions (8)Used By (1)

Dropdown (Bootstrap Extension)
==============================

[](#dropdown-bootstrap-extension)

This extension wraps a Bootstrap dropdown into a reusable JavaScript class (`Dropdown`) and adds:

- a searchable dropdown input
- a hidden input for stable form values
- dynamic item loading/replacement
- programmatic selection and reset
- optional swipe actions per item
- optional List.js integration

Purpose and Use Cases
---------------------

[](#purpose-and-use-cases)

Use this when a plain Bootstrap dropdown is not enough, for example:

- large selectable lists with live filtering
- forms that must submit a stable value (`key`) through a hidden field
- dynamic data sources (Ajax/reload) without rebuilding markup manually
- extra interactions such as swipe delete or preselection

Requirements
------------

[](#requirements)

- Bootstrap 5 (or 4 via the built-in `window.bs4` fallback)
- jQuery (used internally)
- optional: List.js when using `listjs: true`

Quick Start
-----------

[](#quick-start)

HTML:

```

```

JavaScript:

```
const dd = new Dropdown('countryDropdown', {
  placeholder: 'Select country',
  items: {
    de: { description: 'Germany' },
    at: { description: 'Austria' },
    ch: { description: 'Switzerland' }
  },
  onSelected: () => {
    const selected = dd.selected();
    console.log('Selected:', selected?.key, selected?.description);
  }
});
```

The selected value is stored in the hidden input with `name="countryDropdown"`.

Initialization: Full Options List
---------------------------------

[](#initialization-full-options-list)

```
const dd = new Dropdown('exampleDropdown', {
  bootstrapmajor: 5,
  buttonstyle: 'btn-outline-secondary',
  caret: true,
  disabled: false,
  floatingbox: false,
  items: {},
  listjs: false,
  filter: true,
  menumaxheight: '300px',
  menustyle: '',
  placeholder: '',
  required: false,
  swipe: {
    left: {
      hint: false,
      action: false,
      condition: (idx, item, li) => true
    },
    right: {
      hint: false,
      action: false,
      condition: (idx, item, li) => true
    }
  },
  onSelected: e => {},
  onInput: (event, input) => {},
  onReplaceText: undefined,
  item: 'Entry',
  valueNames: [],
  valueKey: undefined,
  bootstrapAutoClose: undefined
});
```

OptionTypeDefaultDescription`bootstrapmajor``number``5`Bootstrap major version (`5` or `4`).`buttonstyle``string``'btn-outline-secondary'`Extra classes on the toggle button.`caret``boolean``true`Shows/hides the caret on the button (`false` disables it).`disabled``boolean``false`Disables input, toggle, and hidden input.`floatingbox``boolean``false`Enables Bootstrap floating-label behavior (with `filter: true`).`items``object``{}`Initial entries. Keys become `data-value` / hidden-input value.`listjs``boolean``false`Enables List.js mode instead of native menu rendering.`filter``boolean``true`Enables/disables searchable input (`false` = button label only).`menumaxheight``string``'300px'`Menu max-height (inline style).`menustyle``string``''`Additional inline style for the menu.`placeholder``string``''`Placeholder for search input or label placeholder when `filter: false`.`required``boolean``false`Sets `required` on the search input.`swipe.left.hint``string|false``false`HTML hint for left swipe (for example an icon).`swipe.left.action``function|false``false`Callback on valid left swipe (`(event, li) => {}`).`swipe.left.condition``function``(item) => true`Condition to allow left swipe (`(idx, item, li) => boolean`).`swipe.right.hint``string|false``false`HTML hint for right swipe.`swipe.right.action``function|false``false`Callback on valid right swipe (`(event, li) => {}`).`swipe.right.condition``function``(item) => true`Condition to allow right swipe (`(idx, item, li) => boolean`).`onSelected``function``(e) => {}`Runs after an item is selected.`onInput``function``(event, input) => {}`Runs while typing/filtering.`onReplaceText``function|undefined``undefined`Overrides default display-text replacement (click/focusout).`item``string``'Entry'`List.js item template (`listjs: true`).`valueNames``array``[]`List.js field definitions (`listjs: true`).`valueKey``string|undefined``auto`Forces which List.js item field is used as internal key.`bootstrapAutoClose``boolean|undefined``undefined`Relevant only for Bootstrap 4 fallback; `false` prevents `hide.bs.dropdown`.Item Structure
--------------

[](#item-structure)

A single `items` entry currently supports:

```
items: {
  de: {
    description: 'Germany', // string | Element | { short, extended }
    disabled: false,        // optional
    active: false,          // optional, marks item as active/preselected
    selected: false,        // optional
    dataList: {             // optional extra attributes for item button
      'data-country-code': 'DE'
    }
  }
}
```

Usage Snippets
--------------

[](#usage-snippets)

### 1. Set items dynamically

[](#1-set-items-dynamically)

```
dd.setItems({
  fr: { description: 'France' },
  it: { description: 'Italy' }
});
```

### 2. Select programmatically

[](#2-select-programmatically)

```
await dd.selected('it'); // triggers click on item with key "it"
```

### 3. Clear selection / input

[](#3-clear-selection--input)

```
dd.clear({
  resetSelection: true,
  resetInput: true,
  close: true
});
```

### 4. Disable/enable dropdown

[](#4-disableenable-dropdown)

```
dd.setDisabled(true);  // disable
dd.setDisabled(false); // enable
```

### 5. Swipe action on list entries

[](#5-swipe-action-on-list-entries)

```
const taskDd = new Dropdown('taskDropdown', {
  items: {
    1: { description: 'Task A' },
    2: { description: 'Task B' }
  },
  swipe: {
    left: {
      hint: '',
      action: (event, li) => {
        console.log('Delete:', li);
        return true; // true => entry is removed with animation
      }
    }
  }
});
```

### 6. Dispose cleanly (for example before DOM removal)

[](#6-dispose-cleanly-for-example-before-dom-removal)

```
dd.dispose();
```

Important Methods (Short Overview)
----------------------------------

[](#important-methods-short-overview)

- `setItems(items, callback?, options?)`: add new entries / re-render
- `selected()`: get currently selected item
- `selected(key)`: select item by key
- `selected(null)`: clear current selection
- `clear(options?)`: clear items/selection in a controlled way
- `setDisabled(state)`: enable/disable interaction
- `getInput()`: current visible input text
- `matchItem()`: number of exact matches for current input
- `dispose()`: remove listeners/instance safely

Notes
-----

[](#notes)

- With `filter: false`, the component uses a button label instead of a search input.
- When `listjs: true`, List.js must be available, otherwise initialization is incomplete.
- The container dispatches custom events including `dropdown-items-rendered`.

###  Health Score

35

—

LowBetter than 80% of packages

Maintenance85

Actively maintained with recent releases

Popularity3

Limited adoption so far

Community8

Small or concentrated contributor base

Maturity40

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~27 days

Recently: every ~37 days

Total

7

Last Release

77d ago

### Community

Maintainers

![](https://www.gravatar.com/avatar/fd6ae4a08589eb1cfe426565dc5668babde2ff376104c63a764a296db832a7b3?d=identicon)[braesident](/maintainers/braesident)

---

Top Contributors

[![braesident](https://avatars.githubusercontent.com/u/13104491?v=4)](https://github.com/braesident "braesident (12 commits)")

### Embed Badge

![Health badge](/badges/braesident-dropdown/health.svg)

```
[![Health](https://phpackages.com/badges/braesident-dropdown/health.svg)](https://phpackages.com/packages/braesident-dropdown)
```

###  Alternatives

[wyrihaximus/react-child-process-messenger

Messenger decorator for react/child-process

32279.4k4](/packages/wyrihaximus-react-child-process-messenger)[inpsyde/object-hooks-remover

Package to remove WordPress hook callbacks that uses object methods or closures.

6256.4k1](/packages/inpsyde-object-hooks-remover)[elephox/mimey

PHP package for converting file extensions to MIME types and vice versa.

16217.1k5](/packages/elephox-mimey)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
