mirror of
https://github.com/tenrok/vue-select.git
synced 2026-06-07 07:12:23 +03:00
update demo site to use Vuex (just a proof of concept), overhaul look and feel
This commit is contained in:
+25
-162
@@ -1,37 +1,27 @@
|
||||
<style>
|
||||
<style lang="scss">
|
||||
|
||||
/* #F16745 #FFC65D #7BC8A4 #4CC3D9 #93648D #404040 */
|
||||
@import 'variables.scss';
|
||||
|
||||
body {
|
||||
color: #404040;
|
||||
}
|
||||
|
||||
.jumbotron-top {
|
||||
color: #fff;
|
||||
background: #4CC3D9;
|
||||
color: $black;
|
||||
background: $blue;
|
||||
background: linear-gradient(to top, rgba(76,195,217,1) 0%,rgba(152,227,234,1) 100%);
|
||||
// background: linear-gradient(45deg, rgba(76,195,217,1) 0%,rgba(152,227,234,1) 100%);
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
.btn-custom {
|
||||
color: #fff;
|
||||
background: #F16745;
|
||||
}
|
||||
|
||||
.jumbotron.jumbotron-green {
|
||||
padding: 75px 0;
|
||||
/*background: #404040;*/
|
||||
/*color: #fff;*/
|
||||
}
|
||||
|
||||
#v-select .dropdown-toggle {
|
||||
/*border-color:#fff;*/
|
||||
background: #fff;
|
||||
}
|
||||
|
||||
#v-select .dropdown-toggle:after {
|
||||
color: #404040;
|
||||
}
|
||||
|
||||
/* Cyan theme */
|
||||
#v-select .selected-tag {
|
||||
color: #147688;
|
||||
@@ -54,169 +44,42 @@
|
||||
background: #4CC3D9;
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
#output {
|
||||
height: 200px;
|
||||
border: none;
|
||||
color: #404040;
|
||||
}
|
||||
</style>
|
||||
|
||||
<template>
|
||||
<div class="jumbotron jumbotron-top">
|
||||
<div class="container">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<h1>Vue Select</h1>
|
||||
<p class="lead">A simple component that provides similar functionality to Select2 without the overhead of jQuery.</p>
|
||||
<a class="btn btn-custom" href="https://github.com/sagalbot/vue-select">View on GitHub</a>
|
||||
<p class="lead">A well-tested Vue.js component that provides similar functionality to Select2/Chosen without the overhead of jQuery.</p>
|
||||
<!-- <p>Vue-select has no JavaScript dependencies</p> -->
|
||||
<ul class="unstyled lead">
|
||||
<li>No JS dependencies</li>
|
||||
<li>Works with Vuex</li>
|
||||
<li>Reactive <small>(as you'd expect from a Vue component)</small></li>
|
||||
</ul>
|
||||
|
||||
<a class="btn btn-primary" href="https://github.com/sagalbot/vue-select"><span class="octicon octicon-mark-github"></span> View on GitHub</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<jumbotron></jumbotron>
|
||||
<jumbotron></jumbotron>
|
||||
|
||||
<div id="app" class="container">
|
||||
<h2 class="page-header">Live Edit <small>play around with the above vue-select</small></h2>
|
||||
|
||||
<div class="row">
|
||||
<div class="col-md-6">
|
||||
<label class="control-label">Options</label><br>
|
||||
<div class="radio">
|
||||
<label for="advanced">
|
||||
<input id="advanced" type="radio" v-model="optionType" value="advanced"> Objects
|
||||
<pre><code class="language-javascript">[{value: 'foo', label: 'Foo'}]</code></pre>
|
||||
</label>
|
||||
<br>
|
||||
<label for="simple">
|
||||
<input id="simple" type="radio" v-model="optionType" value="simple"> Strings
|
||||
<pre><code class="language-javascript">['foo', 'bar']</code></pre>
|
||||
</label>
|
||||
<span class="help-block">The <code>options</code> property is watched for changes, and the value is reset anytime the options change. This is useful if you have multiple selection boxes that depend on its ancestors values.</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="col-md-6">
|
||||
|
||||
<div class="form-group">
|
||||
<label class="control-label">Allow Multiple</label>
|
||||
<div class="checkbox">
|
||||
<label class="control-label">
|
||||
<input v-model="multiple" type="checkbox"> True
|
||||
</label>
|
||||
<span class="help-block">Equivalent to the <code>multiple</code> attribute to a <code><select></code>. You'll want to clear any selections you have made before changing this option. It's not one that should be changed after render.</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label class="control-label">Max Height</label>
|
||||
<input type="text" v-model="maxHeight" class="form-control">
|
||||
<span class="help-block">Limit the height of the dropdown menu.</span>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label class="control-label">Placeholder</label>
|
||||
<input type="text" v-model="placeholder" class="form-control">
|
||||
<span class="help-block">Equivalent to the <code>placeholder</code> attribute.</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="container">
|
||||
<div class="col-md-10 col-md-offset-1">
|
||||
<install></install>
|
||||
<params></params>
|
||||
</div>
|
||||
|
||||
<div class="row">
|
||||
<div class="col-md-6">
|
||||
<h2 class="page-header">Install & Usage</h2>
|
||||
<h5>Install from GitHub using NPM</h5>
|
||||
<pre><code class="language-c-like">$ npm install sagalbot/vue-select</code></pre>
|
||||
|
||||
<pre v-pre>
|
||||
<code class="language-markup"><template>
|
||||
<div id="myApp">
|
||||
<v-select :value.sync="selected" :options="options"></v-select>
|
||||
</div>
|
||||
</template></code>
|
||||
|
||||
<code class="language-markup"><script></code>
|
||||
<code class="language-javascript">import vSelect from 'vue-select'
|
||||
export default {
|
||||
components: {vSelect},
|
||||
|
||||
data() {
|
||||
return {
|
||||
selected: null,
|
||||
options: ['foo','bar','baz']
|
||||
}
|
||||
}
|
||||
}</code>
|
||||
<code class="language-markup"></script></code>
|
||||
</pre>
|
||||
</div>
|
||||
<div class="col-md-6">
|
||||
<h2 class="page-header">Parameters</h2>
|
||||
<ul>
|
||||
<li>
|
||||
<code>value</code> Represents the currently selected value(s)
|
||||
<ul>
|
||||
<li>type: String</li>
|
||||
<li>required: true </li>
|
||||
</ul>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<code>options</code> An array of strings or objects to be used as dropdown choices. Supports <code>['foo','bar']</code> & <code>[{label: 'Foo', value: 'foo'}]</code>. When using the <code>[{}]</code> syntax, the objects in the array can have as many properties as you need, as long as the object contains <code>value</code> and <code>label</code> keys.
|
||||
<ul>
|
||||
<li>type: Array</li>
|
||||
<li>default: []</li>
|
||||
</ul>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<code>maxHeight</code> Limit the height of the dropdown menu
|
||||
<ul>
|
||||
<li>type: String</li>
|
||||
<li>default: '400px'</li>
|
||||
</ul>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<code>searchable</code> Toggle filtering of options
|
||||
<ul>
|
||||
<li>type: Boolean</li>
|
||||
<li>default: true</li>
|
||||
</ul>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<code>multiple</code> Equivalent to <code>multiple</code> attribute on a <code><select></code>
|
||||
<ul>
|
||||
<li>type: Boolean</li>
|
||||
<li>default: true</li>
|
||||
</ul>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<code>placeholder</code> Equivalent to <code>placeholder</code> attribute on an <code><input></code>
|
||||
<ul>
|
||||
<li>type: String</li>
|
||||
<li>default: ''</li>
|
||||
</ul>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<code>transition</code> Vue <code>transition</code> prop applied to the <code>.dropdown-menu</code>
|
||||
<ul>
|
||||
<li>type: Boolean</li>
|
||||
<li>default: true</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Jumbotron from './components/Jumbotron.vue'
|
||||
import Install from './components/Install.vue'
|
||||
import Params from './components/Params.vue'
|
||||
|
||||
export default {
|
||||
components: {Jumbotron},
|
||||
components: { Jumbotron, Params, Install },
|
||||
}
|
||||
</script>
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
$orange: #F16745;
|
||||
$yellow: #FFC65D;
|
||||
$green: #7BC8A4;
|
||||
$blue: #4CC3D9;
|
||||
$purple: #93648D;
|
||||
$black: #404040;
|
||||
|
||||
// Code
|
||||
$code-blue: #66d9ef;
|
||||
$code-purple: #ae81ff;
|
||||
$code-black: #272822;
|
||||
$code-white: #f8f8f2;
|
||||
$code-grey: #708090;
|
||||
$code-green: #a6e22e;
|
||||
|
||||
@@ -0,0 +1,31 @@
|
||||
<template>
|
||||
<h2 class="page-header">Install & and Usage</h2>
|
||||
<p>Install from GitHub via NPM</p>
|
||||
<pre><code class="language-bash">npm install sagalbot/vue-select</code></pre>
|
||||
|
||||
<pre v-pre>
|
||||
<code class="language-markup"><template>
|
||||
<div id="myApp">
|
||||
<v-select :value.sync="selected" :options="options"></v-select>
|
||||
</div>
|
||||
</template></code>
|
||||
|
||||
<code class="language-markup"><script></code>
|
||||
<code class="language-javascript">import vSelect from 'vue-select'
|
||||
export default {
|
||||
components: {vSelect},
|
||||
|
||||
data() {
|
||||
return {
|
||||
selected: null,
|
||||
options: ['foo','bar','baz']
|
||||
}
|
||||
}
|
||||
}</code><code class="language-markup">
|
||||
</script></code>
|
||||
</pre>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {}
|
||||
</script>
|
||||
+190
-22
@@ -1,44 +1,212 @@
|
||||
<template>
|
||||
<div class="jumbotron jumbotron-green">
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-6 col-md-offset-1">
|
||||
<div class="jumbotron">
|
||||
<div class="flex-container">
|
||||
<div transition="slide-right" v-show="selected" class="flex code">
|
||||
<pre>{{ selected | json }}</pre>
|
||||
</div>
|
||||
|
||||
<div class="flex center">
|
||||
<v-select
|
||||
id="v-select"
|
||||
:placeholder="placeholder"
|
||||
:value.sync="select"
|
||||
:options="options[optionType]"
|
||||
:multiple="multiple">
|
||||
:value="selected"
|
||||
:options="options"
|
||||
:multiple="multiple"
|
||||
:on-change="setSelected"
|
||||
>
|
||||
</v-select>
|
||||
|
||||
</div>
|
||||
|
||||
<pre id="output" class="col-md-4">{{ select | json }}</pre>
|
||||
<div class="flex code">
|
||||
<div>
|
||||
<pre class="fake">
|
||||
/**<br>
|
||||
* @prop multiple <br>
|
||||
* @type {Boolean} <br>
|
||||
*/
|
||||
</pre>
|
||||
<a @click="toggleMultiple" class="btn btn-code" :class="{ active: multiple }">Multiple</a>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<pre class="fake">
|
||||
/**<br>
|
||||
* @prop options <br>
|
||||
* @type {Array} <br>
|
||||
*/
|
||||
</pre>
|
||||
<a @click="toggleOptionType" class="btn btn-code">
|
||||
<span :class="{active: type === 'advanced'}">[{label:'foo'}]</span> <span class="grey">||</span> <span :class="{active: type === 'simple'}">['foo']</span>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<pre class="fake">
|
||||
/**<br>
|
||||
* @prop placeholder <br>
|
||||
* @type {String} <br>
|
||||
*/
|
||||
</pre>
|
||||
<input @keyup="onPlaceholderChange" type="text" class="btn btn-code" value="{{ placeholder }}">
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import vSelect from './Select.vue'
|
||||
import { setSelected, toggleMultiple, setPlaceholder, toggleOptionType } from '../vuex/actions'
|
||||
|
||||
export default {
|
||||
components: { vSelect },
|
||||
|
||||
data() {
|
||||
return {
|
||||
select: null,
|
||||
placeholder: 'Choose a Country',
|
||||
multiple: true,
|
||||
maxHeight: '400px',
|
||||
options: {
|
||||
advanced: require('../countries/countries.js'),
|
||||
simple: require('../countries/simpleCountries.js'),
|
||||
simpler: [{label: 'This is Foo', value: 'foo'}, {label: 'This is Bar', value: 'bar'}, {label: 'This is Baz', value: 'baz'}],
|
||||
vuex: {
|
||||
getters: {
|
||||
placeholder (store) {
|
||||
return store.placeholder
|
||||
},
|
||||
optionType: 'simple'
|
||||
selected (store) {
|
||||
return store.selected
|
||||
},
|
||||
type (store) {
|
||||
return store.optionType
|
||||
},
|
||||
options (store) {
|
||||
return store.options[store.optionType]
|
||||
},
|
||||
multiple (store) {
|
||||
return store.multiple
|
||||
}
|
||||
},
|
||||
actions: { setSelected, toggleMultiple, setPlaceholder, toggleOptionType }
|
||||
},
|
||||
methods: {
|
||||
onPlaceholderChange ( e ) {
|
||||
this.setPlaceholder( e.target.value )
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="sass">
|
||||
@import '../variables';
|
||||
|
||||
.slide-right-transition {
|
||||
opacity: 1;
|
||||
transition: all .5s;
|
||||
}
|
||||
|
||||
.slide-right-enter, .slide-right-leave {
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
.jumbotron {
|
||||
padding: 0;
|
||||
background: rgba($green, .1);
|
||||
}
|
||||
|
||||
.grey {
|
||||
color: $code-grey;
|
||||
}
|
||||
|
||||
.flex-container {
|
||||
padding: 0;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-direction: row;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.flex {
|
||||
display:flex;
|
||||
align-self: stretch;
|
||||
padding: 0 34px;
|
||||
}
|
||||
|
||||
.flex.code:first-child {
|
||||
width: 250px;
|
||||
color: $code-white;
|
||||
align-items: center;
|
||||
// flex-grow: 1;
|
||||
}
|
||||
|
||||
.flex.center {
|
||||
width: 100%;
|
||||
align-self: center;
|
||||
text-align: center;
|
||||
|
||||
#v-select {
|
||||
width: 70%;
|
||||
margin: 0 auto;
|
||||
}
|
||||
}
|
||||
|
||||
.flex.code:last-child {
|
||||
// flex-grow: 1;
|
||||
width: 280px;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.code {
|
||||
background: $code-black;
|
||||
// color: $code-white;
|
||||
text-shadow: 0 1px rgba(0, 0, 0, 0.3);
|
||||
font-family: Consolas, Monaco, 'Andale Mono', 'Ubuntu Mono', monospace;
|
||||
text-align: left;
|
||||
padding: 48px 15px;
|
||||
|
||||
.active {
|
||||
color: $code-green;
|
||||
}
|
||||
}
|
||||
|
||||
.btn-code {
|
||||
display: inline-block;
|
||||
float: left;
|
||||
clear: both;
|
||||
margin-bottom: 7px;
|
||||
border: 1px solid $code-white;
|
||||
color: $code-white;
|
||||
box-shadow: none;
|
||||
background: none;
|
||||
text-shadow: 0 1px rgba(0, 0, 0, 0.3);
|
||||
|
||||
&:focus,
|
||||
&:active,
|
||||
&:hover,
|
||||
&.active {
|
||||
color: $code-green;
|
||||
border: 1px solid $code-green;
|
||||
outline: none;
|
||||
box-shadow: none;
|
||||
appearance: none;
|
||||
|
||||
.active {
|
||||
color: $code-grey;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.btn-code + pre {
|
||||
margin-top: 15px;
|
||||
}
|
||||
|
||||
input.btn-code {
|
||||
text-align: left;
|
||||
|
||||
}
|
||||
|
||||
pre {
|
||||
background: none;
|
||||
border: none;
|
||||
color: $code-white;
|
||||
}
|
||||
|
||||
pre.fake {
|
||||
padding: 0;
|
||||
white-space: normal;
|
||||
border: none;
|
||||
background: $code-black;
|
||||
color: $code-grey;
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,99 @@
|
||||
<template>
|
||||
<h2 class="page-header">Parameters</h2>
|
||||
<pre v-pre><code class="language-javascript">props: {
|
||||
|
||||
/**
|
||||
* Contains the currently selected value. Very similar to a
|
||||
* `value` attribute on an &lt;input&gt;. In most cases, you'll want
|
||||
* to set this as a two-way binding, using :value.sync. However,
|
||||
* this will not work with Vuex, in which case you'll need to use
|
||||
* the onChange callback property.
|
||||
* @type {Object||String||null}
|
||||
*/
|
||||
value: {
|
||||
default: null
|
||||
},
|
||||
|
||||
/**
|
||||
* An array of strings or objects to be used as dropdown choices.
|
||||
* If you are using an array of objects, vue-select will look for
|
||||
* a `label` key (ex. [{label: 'This is Foo', value: 'foo'}]). A
|
||||
* custom label key can be set with the `label` prop.
|
||||
* @type {Array}
|
||||
*/
|
||||
options: {
|
||||
type: Array,
|
||||
default() { return [] },
|
||||
},
|
||||
|
||||
/**
|
||||
* Enable/disable filtering the options.
|
||||
* @type {Boolean}
|
||||
*/
|
||||
searchable: {
|
||||
type: Boolean,
|
||||
default: true
|
||||
},
|
||||
|
||||
/**
|
||||
* Equivalent to the `multiple` attribute on a `<select>` input.
|
||||
* @type {Boolean}
|
||||
*/
|
||||
multiple: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
|
||||
/**
|
||||
* Equivalent to the `placeholder` attribute on an `<input>`.
|
||||
* @type {String}
|
||||
*/
|
||||
placeholder: {
|
||||
type: String,
|
||||
default: ''
|
||||
},
|
||||
|
||||
/**
|
||||
* Sets a Vue transition property on the `.dropdown-menu`. vue-select
|
||||
* does not include CSS for transitions, you'll need to add them yourself.
|
||||
* @type {String}
|
||||
*/
|
||||
transition: {
|
||||
type: String,
|
||||
default: 'expand'
|
||||
},
|
||||
|
||||
/**
|
||||
* Enables/disables clearing the search text when an option is selected.
|
||||
* @type {Boolean}
|
||||
*/
|
||||
clearSearchOnSelect: {
|
||||
type: Boolean,
|
||||
default: true
|
||||
},
|
||||
|
||||
/**
|
||||
* Tells vue-select what key to use when generating option labels when
|
||||
* `option` is an object.
|
||||
* @type {String}
|
||||
*/
|
||||
label: {
|
||||
type: String,
|
||||
default: 'label'
|
||||
},
|
||||
|
||||
/**
|
||||
* An optional callback function that is called each time the selected
|
||||
* value(s) change. When integrating with Vuex, use this callback to trigger
|
||||
* an action, rather than using :value.sync to retreive the selected value.
|
||||
* @type {Function}
|
||||
* @default {null}
|
||||
*/
|
||||
onChange: Function
|
||||
}
|
||||
</code></pre>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {}
|
||||
</script>
|
||||
@@ -2,6 +2,8 @@ import Vue from 'vue'
|
||||
import App from './App.vue'
|
||||
import store from './vuex/store'
|
||||
|
||||
Vue.config.debug = true
|
||||
|
||||
/* eslint-disable no-new */
|
||||
new Vue({
|
||||
el: 'body',
|
||||
|
||||
+12
-11
@@ -1,14 +1,15 @@
|
||||
export const increment = ({ dispatch }) => dispatch('INCREMENT')
|
||||
export const decrement = ({ dispatch }) => dispatch('DECREMENT')
|
||||
|
||||
export const incrementIfOdd = ({ dispatch, state }) => {
|
||||
if ((state.count + 1) % 2 === 0) {
|
||||
dispatch('INCREMENT')
|
||||
}
|
||||
export const setSelected = ({ dispatch }, selected) => {
|
||||
dispatch('SET_SELECTED', selected)
|
||||
}
|
||||
|
||||
export const incrementAsync = ({ dispatch }) => {
|
||||
setTimeout(() => {
|
||||
dispatch('INCREMENT')
|
||||
}, 1000)
|
||||
export const toggleOptionType = ({ dispatch }) => {
|
||||
dispatch('TOGGLE_OPTION_TYPE')
|
||||
}
|
||||
|
||||
export const setPlaceholder = ({ dispatch }, placeholder) => {
|
||||
dispatch('SET_PLACEHOLDER', placeholder)
|
||||
}
|
||||
|
||||
export const toggleMultiple = ({ dispatch }) => {
|
||||
dispatch('TOGGLE_MULTIPLE')
|
||||
}
|
||||
+30
-5
@@ -5,15 +5,40 @@ Vue.use(Vuex)
|
||||
Vue.config.debug = true
|
||||
|
||||
const state = {
|
||||
count: 0
|
||||
selected: null,
|
||||
placeholder: 'Select a Country',
|
||||
multiple: true,
|
||||
maxHeight: '400px',
|
||||
options: {
|
||||
advanced: require('../countries/advanced.js'),
|
||||
simple: require('../countries/simple.js'),
|
||||
},
|
||||
optionType: 'advanced'
|
||||
}
|
||||
|
||||
const mutations = {
|
||||
INCREMENT (state) {
|
||||
state.count++
|
||||
SET_SELECTED (state, selected) {
|
||||
state.selected = selected
|
||||
},
|
||||
DECREMENT (state) {
|
||||
state.count--
|
||||
|
||||
TOGGLE_OPTION_TYPE (state) {
|
||||
if( state.optionType === 'advanced' ) {
|
||||
state.optionType = 'simple'
|
||||
} else {
|
||||
state.optionType = 'advanced'
|
||||
}
|
||||
},
|
||||
|
||||
SET_PLACEHOLDER (state, placeholder) {
|
||||
state.placeholder = placeholder
|
||||
},
|
||||
|
||||
TOGGLE_MULTIPLE (state) {
|
||||
state.multiple = ! state.multiple
|
||||
},
|
||||
|
||||
SET_MAX_HEIGHT (state, maxHeight) {
|
||||
state.maxHeight = maxHeight
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user