npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

vue-dropdown-advanced

v0.1.4

Published

A seriously advanced Vue Dropdown tool with many custom options.

Downloads

6

Readme

An advanced Vue Dropdown Component

An advanced pure Vue Dropdown control with many customisable options.

Key features

  • caters for different types of dropdown items (action, checkbox, radio, header, seperator)
  • lazily calls back for dropdown items (synchronously or asynchronously!)
  • images are supported on left and on the right (multiple)
  • dropdown items are removed from the markup when dropdown is closed
  • dropdown location is configurable (left/right/up/down)
  • the dropdown can be created through code using any html element as source
  • and much more!

Demo

Check it out at demo-page!

Typescript

The code snippets below are extracts from the demo project. An index.d.ts file providing intellisense will be included soon.

Setup

import Vue from 'vue';
import { DropDownMenu, DropDownInfo, DropDownItemBase, HeaderItem, ActionItem, CheckboxItem, RadioboxItem, SeperatorItem } from "vue-dropdown-advanced";

import 'vue-dropdown-advanced/dist/vue-dropdown-advanced.css';

import '@mdi/font/css/materialdesignicons.css';

include the vue-dropdown-advanced.css

Make sure you include the vue-dropdown-advanced.css file in your main imports.

import 'vue-dropdown-advanced/dist/vue-dropdown-advanced.css

include the materialdesignicons.css

If you wish to use images then also include the scoped @mdi/font/css/materialdesignicons.css (you must have '@mdi/font' as a dependency in your project)

import '@mdi/font/css/materialdesignicons.css'

Using the Vue DropDown

A basic 'fixed' dropdown items

down-right.png

We 'attach' a DropDownMenu menu to the 'Example Down Right' div simply by nesting it within its parent element as shown in the Vue template below. This is imporant since a 'click' handler is attached to this parent so the dropdown can be toggled when clicked.

There is also a programmatic way of attaching this dropdown to any DOM element - more on this later.

/// The 'template' part of the Vue file
<div class='button example-dr'>
	Example Down Right
	<drop-down-menu :items="fixedItems" @click="this.onClick">  </drop-down-menu>
</div>

Notice we have bound the 'items' property to the 'fixedItems' data property of the vue model. When the parent is 'clicked' the onClick handler is called with the item itself but also any other dropdown state.

/// The 'javascript' part of the Vue file		
export default Vue.extend({
  name: "app",
  data: () => {
    const fixedItems: DropDownItemBase[] = [];
    return {
      fixedItems
    }
  },
  methods: {
      onClick(info: DropDownInfo) {
        let msg = `Item '${info.item.text}' was clicked. [key: ${info.item.key}] `;
        console.log(msg);
      },
  },
  components: {
    DropDownMenu
  },
  created() {
    this.fixedItems.push(new ActionItem("A", "Holiday in France", "", false, _ => alert(_.key)));
    this.fixedItems.push(new ActionItem("B", "Go to California"));
    this.fixedItems.push(new ActionItem("C", "Visit London"));
  }
});

Bit boring, let's see what else we can do.

Show-casing the dropddown advanced

down-right.png

That is more like it!

Again, we 'attach' a DropDownMenu menu to the 'Example Down Right' div by nesting it within its div as shown in the Vue template below.

/// The 'template' part of the Vue file
<div class='button example-dr'>
	Showcase
	<drop-down-menu :items="fixedItems" @click="this.onClick">  </drop-down-menu>
</div>

Again, we are binding the 'items' property to the 'fixedItems' data property of the vue model. When the parent is 'clicked' the onClick handler is called with the item itself but also any other dropdown state.

/// The 'javascript' part of the Vue file		
var item = new ActionItem("booknow", "Book now!", "mdi-airplane-takeoff");
item.data = { pos: context };                            // save some random data with this item..
item.addRightImage("mdi-cogs", "settings");
item.addRightImage("mdi-exit-to-app", "exit the application");

fixedItems.push(item);
fixedItems.push(new SeperatorItem());
fixedItems.push(new HeaderItem("Choose your destination:"));
fixedItems.push(new RadioboxItem("california", "California and Santa Monica", "A"));
fixedItems.push(new RadioboxItem("newyork", "New York", "A"));
fixedItems.push(new RadioboxItem("miami", "Miami", "A"));
fixedItems.push(new SeperatorItem());
fixedItems.push(new HeaderItem("Mode of transport:"));
fixedItems.push(new RadioboxItem("car", "By car", "B"));
fixedItems.push(new RadioboxItem("boat", "By boat", "B", true));
fixedItems.push(new RadioboxItem("plane", "By plane", "B"));
fixedItems.push(new SeperatorItem());
fixedItems.push(new HeaderItem("Choose your activities:"));
fixedItems.push(new CheckboxItem("beach", "Visit the beach"));
fixedItems.push(new CheckboxItem("town", "Walk through town"));
fixedItems.push(new CheckboxItem("park", "Visit Parks"));
fixedItems.push(new CheckboxItem("hirecar", "Hire a car"));
fixedItems.push(new CheckboxItem("nothing", "Do absolutely nothing !"));

onClick(info: DropDownInfo) {
	// info.item		-> the selected item
	// info.items		-> all the source items that are shown
	// info.imageOnRight	-> (RightImageInfo) details regarding the right image if it was clicked
},

Note the groupBy property available on Radiobox items. Identical groupBy values will force a mutually exclusive group to be created, ie only a single radiobox can be 'checked' within a group. Hence in the example above we have two groups; one with groupBy marker 'A', the other with value 'B'. These identifiers could be any unique string.

Right placed Images

Images placed on the right of the text are selectable and therefore can be 'listened' for.

down-right.png

Use the addRightImage method to add a 'right aligned' image to an ActionItem. The first param is a materialdesignicons identifier, the second is an optional tooltip.

...
var item = new ActionItem("booknow", "Book now!", "mdi-airplane-takeoff");
item.data = { pos: context };                            // save some random data with this item..
item.addRightImage("mdi-cogs", "settings");              
item.addRightImage("mdi-exit-to-app", "exit the application");
...

Dropdown Direction

The dropdown doesn't necessarily has to go 'down' :) It can also go up as well as be left or right aligned. This is controlled through the direction property.
The default is down-right but it can be set to down-left, up-left or up-right - see examples below.

down-right.png

/// The 'template' part of the Vue file (NOTE the 'direction' property)
<div class='button'>
   Example Up Left
   <drop-down-menu :items="myitems_ul" @click="this.onClick" direction="up-left"></drop-down-menu>
</div>

Retrieving dropdown items asynchronously

An asynchronous request for data can be made by binding a function to the itemsAsync prop of the DropDownMenu. This function is expected to return an array of DropDown items. This is extremely useful when dropdown items can only be determined at runtime.

/// The 'template' part of the Vue file
<div class='button'>
   Example Up Left
   <drop-down-menu :itemsAsync="getAsyncItems" @click="this.onClick">  </drop-down-menu>
</div>
  methods: {
      onClick(info: DropDownInfo) {
        ...
      },
      async getAsyncItems() {
        await delay(1000);      // call an api for (dropdown) data (async)
        // .. convert the data to DropDownItems ...
        return this.myitems_dr; // return these items
      },
  },

Max/Min dropdown sizing

A certain minimum or maximum of the dropdown can be enforced by providing a min-width, max-width or max-height property as shown below. Specify the value including the unit ('px' in this case).

/// The 'template' part of the Vue file
<div class='button'>
   Example Up Left
   <drop-down-menu :itemsAsync="getAsyncItems" @click="this.onClick" min-width="240px">  </drop-down-menu>
</div>

How to use this programmatically

In cases where you just want to attach the dropdown to an DOM existing element anywhere on your form without altering your template you can use the DropDownControl class.

  1. Simply create a new DropDownControl object passing in the element you wish to attach the dropdown to. This could be any html element.
  2. Assign the dropdown items to show
  3. Attach an event handler(s)
  4. Set some specific properties (like minWidth or OpenOnCreate)
  5. Once configured call 'createMenu()' which will create and prepare the dropdown control

In its simplest form it would look something like this:

static demo1 = () => {
    
    let el = document.getElementsByClassName("example-programmatically");

    // specify the dropdown items
    let items = [];
    items.push(new ActionItem("logout", "Logout", "mdi-exit-run", false, _ => alert(_.key)));
		items.push(new SeperatorItem());
		items.push(new ActionItem("profile", "Show Profile", "mdi-face"));
		items.push(new ActionItem("shortcuts", "Show Shortcuts", "mdi-access-point"));
		items.push(new ActionItem("setting", "System Settings and a whole lot more and stuff", "mdi-cogs"));

    // 1. create a new DropDownControl for this element
    var dd: DropDownControl = new DropDownControl(el[0]);

    // 2. assign the items to diplay when clicked
    dd.items = items;

    // 3. set a handler when the user selects an item
    dd.onClick = (info: DropDownInfo) => {
      debugger;
      console.log(info.item.key);  // etc...
    }

    // 4. set some more specific properties
    dd.openOnCreate = true;
    dd.minWidth = "300px"
    dd.maxHeight = "150px";
    
    // 5. create the vue dropdown control
    dd.createMenu();
}

History

|version | Notes | | ---- | ------ | v 0.1.4 | security risk package updates v 0.1.3 | css updates v 0.1.2 | introduction of the DropDownControl allowing full programmatic control v 0.1.1 | dropdown now supports min-width, max-width and max-height properties v 0.1.0 | introduced @click event handler in addition to :click callback v 0.0.11 | cleaned package - separated css and materialdesignicons.css v 0.0.10 | exporting more helper objects (like getTestItems, delay, createGuidRight5) v 0.0.9 | small fixes v 0.0.1..8 | Initial release - work in progress