Skip to content

Adding Vue-Multiselect #21

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Aug 8, 2016
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 40 additions & 0 deletions dev/schema.js
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,46 @@ module.exports = {
hint: "Minimum 6 characters",
styleClasses: "half-width",
validator: validators.string
},

{
type: "vueMultiSelect",
label: "Skills (vue-multiSelect field)",
model: "skills",
required: true,
multiSelect: true,
selectOptions: {
// id:25,
// key:"name",
// label: "name",
searchable:true,
clearOnSelect:true,
hideSelected:true,
// maxHeight:300,
// allowEmpty:true,
// resetAfter:false,
closeOnSelect: true,
// customLabel:function(){return ""},
taggable:true,
tagPlaceholder:'Press enter to create a tag',
Copy link
Member

@icebob icebob Aug 3, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please add an onNewTag event handler to the selectOptions:

selectOptions {
  ...
  onNewTag: function(...) { console.log(...); },
  ...
}

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm also adding onSearch (from onSearchChange) since it is a very useful function (to create dynamics option list for country and all kind of filtering).

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

OK, great!

max:4
},
values: [
"HTML5",
"Javascript",
"CSS3",
"CoffeeScript",
"AngularJS",
"ReactJS",
"VueJS"
],
onChanged(model, newVal, oldVal, field) {
console.log(`Model's name changed from ${oldVal} to ${newVal}. Model:`, model);
},
min: 2,
max: 4,
placeholder:"Select one Vue",
validator: validators.array
},

{
Expand Down
3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,7 @@
},
"dependencies": {
"babel-runtime": "6.9.2",
"vue": "1.0.24"
"vue": "1.0.24",
"vue-multiselect": "^1.0.1"
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove from dependencies and load as an external optional component.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't have a cdnjs or jsdelivr link for vue-multiselect. I used rawgit, I hope it is enough.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, rawgit enough. It is only a developer example file.
Please update package.json from master. Yesterday I updated dependencies #24 and you have conflict with it currently.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How do I do that ? I have forked the project, but I don't know how to update my fork.
Also, I can't seem to make vue-multiselect a optional dependency without breaking everything.
I'm currently using components to make multiselect available to the template, but I don't know how to load it optionally. I tried with a function that return either an empty object or the component definition from the lib (VueMultiselect.Multiselect). It fail badly.
I can't really do like bootstrap-select or ionRangeSlider because vue-multiselect is really tied to Vue.
Help ?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I made a fiddle: http://www.webpackbin.com/4yy1cQ2OW
Just load the lib with a script tag. In the fieldMultiselect.vue check the lib loaded and register as a global component.

Copy link
Member

@icebob icebob Aug 4, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Easy way to rebase package.json, copy from master from this repo, and paste your branch :) And there won't be diff.

}
}
86 changes: 86 additions & 0 deletions src/fields/fieldVueMultiSelect.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
<template lang="jade">
multiselect(
:id="schema.selectOptions.id",
:options="options",
:multiple="schema.multiSelect",
:selected="value",
:key="schema.selectOptions.key || null",
:label="schema.selectOptions.label || null",
:searchable="schema.selectOptions.searchable",
:clear-on-select="schema.selectOptions.clearOnSelect",
:hide-selected="schema.selectOptions.hideSelected",
:placeholder="schema.placeholder",
:max-height="schema.selectOptions.maxHeight",
:allow-empty="schema.selectOptions.allowEmpty",
:reset-after="schema.selectOptions.resetAfter",
:close-on-select="schema.selectOptions.closeOnSelect",
:custom-label="schema.selectOptions.customLabel || null",
:taggable="schema.selectOptions.taggable",
:tag-placeholder="schema.selectOptions.tagPlaceholder",
:max="schema.selectOptions.max",
@update="updateSelected",
@select="onSelect",
@remove="onRemove",
@search-change="onSearchChange",
@tag="addTag",
@open="onOpen",
@close="onClose",
:show-labels="schema.selectOptions.showLabels"
// TODO: add other options from multiSelectMixin
)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please add every fields from multiselect

</template>
<script>
// import { isObject } from "lodash";
import abstractField from "./abstractField";
import Multiselect from "vue-multiselect";

export default {
mixins: [abstractField],
components: {
Multiselect
},
computed: {
options() {
let values = this.schema.values;
if (typeof(values) == "function") {
return values.apply(this, [this.model, this.schema]);
} else {
return values;
}
}
},

methods: {
updateSelected(value, id) {
this.value = value;
},
onSelect(selectedOption, id) {
console.log("onSelect", selectedOption, id);
},
onRemove(removedOption, id) {
console.log("onRemove", removedOption, id);
},
onSearchChange(searchQuery, id) {
console.log("onSearchChange", searchQuery, id);
},
addTag(newTag, id) {
console.log("addTag", newTag, id);
// TODO: implement tag object by sending this function into schema definition
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please call the schema.selectOptions.onNewTag function if it is a function

Copy link
Member Author

@lionel-bijaoui lionel-bijaoui Aug 4, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think about the other events, are they useless or should I add them like onNewTag ?
EDIT: I will comment them for now, since it decrease code coverage stats.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Leave this events in the field code, just comment out the console messages. But I think we only need the addTag event (for the present)

/* const tag = {
name: newTag,
// Just for example needs as we use Array of Objects that should have other properties filled.
// For primitive values you can simply push the tag into options and selected arrays.
code: newTag.substring(0, 2) + Math.floor((Math.random() * 10000000))
}*/
this.options.push(newTag);
this.value.push(newTag);
},
onOpen(id) {
console.log("onOpen", id);
},
onClose(value, id) {
console.log("onClose", value, id);
}
}
};
</script>