[improvement] rename packages dir to src (#3659)

This commit is contained in:
neverland
2019-06-27 11:25:57 +08:00
committed by GitHub
parent 8489918dca
commit 75c79b7044
619 changed files with 21 additions and 21 deletions
+134
View File
@@ -0,0 +1,134 @@
<template>
<demo-section>
<demo-block :title="$t('basicUsage')">
<van-coupon-cell
:coupons="coupons"
:chosen-coupon="chosenCoupon"
@click="showList = true"
/>
<van-popup
v-model="showList"
position="bottom"
>
<van-coupon-list
:coupons="coupons"
:chosen-coupon="chosenCoupon"
:disabled-coupons="disabledCoupons"
@change="onChange"
@exchange="onExchange"
/>
</van-popup>
</demo-block>
</demo-section>
</template>
<script>
/* eslint-disable camelcase */
export default {
i18n: {
'zh-CN': {
coupon: {
name: '优惠券名称',
reason: '优惠券不可用原因',
description: '描述信息'
},
exchange: '兑换成功'
},
'en-US': {
coupon: {
name: 'Coupon name',
reason: 'Coupon unavailable reason',
description: 'Description'
},
exchange: 'Success'
}
},
data() {
return {
showList: false,
chosenCoupon: -1,
exchangedCoupons: []
};
},
computed: {
coupons() {
return [this.coupon, this.discountCoupon, ...this.exchangedCoupons];
},
disabledCoupons() {
return [this.disabledCoupon, this.disabledDiscountCoupon];
},
coupon() {
return {
id: 1,
condition: '无使用门槛\n最多优惠12元',
reason: '',
value: 150,
name: this.$t('coupon.name'),
description: this.$t('coupon.description'),
startAt: 1489104000,
endAt: 1514592000,
valueDesc: '1.5',
unitDesc: '元'
};
},
discountCoupon() {
return {
...this.coupon,
id: 2,
value: 12,
valueDesc: '8.8',
unitDesc: '折'
};
},
disabledCoupon() {
return {
...this.coupon,
id: 3,
reason: this.$t('coupon.reason')
};
},
disabledDiscountCoupon() {
return {
...this.discountCoupon,
valueDesc: '1',
unitDesc: '折',
id: 4,
reason: this.$t('coupon.reason')
};
}
},
methods: {
onChange(index) {
this.showList = false;
this.chosenCoupon = index;
},
onExchange() {
this.$toast(this.$t('exchange'));
this.exchangedCoupons.push({
...this.coupon,
id: this.randomId()
});
},
randomId(max = 999999) {
return Math.floor(Math.random() * max) + 1;
}
}
};
</script>
<style lang="less">
.demo-coupon-list {
.van-popup {
height: 100%;
}
}
</style>
+121
View File
@@ -0,0 +1,121 @@
# Coupon
### Install
``` javascript
import { CouponCell, CouponList } from 'vant';
Vue.use(CouponCell).use(CouponList);
```
## Usage
### Basic Usage
```html
<!-- Coupon Cell -->
<van-coupon-cell
:coupons="coupons"
:chosen-coupon="chosenCoupon"
@click="showList = true"
/>
<!-- Coupon List -->
<van-popup v-model="showList" position="bottom">
<van-coupon-list
:coupons="coupons"
:chosen-coupon="chosenCoupon"
:disabled-coupons="disabledCoupons"
@change="onChange"
@exchange="onExchange"
/>
</van-popup>
```
```javascript
const coupon = {
available: 1,
originCondition: 0,
reason: '',
value: 150,
name: 'Coupon name',
startAt: 1489104000,
endAt: 1514592000,
valueDesc: '1.5',
unitDesc: '元'
};
export default {
data() {
return {
chosenCoupon: -1,
coupons: [coupon],
disabledCoupons: [coupon]
}
},
methods: {
onChange(index) {
this.showList = false;
this.chosenCoupon = index;
},
onExchange(code) {
this.coupons.push(coupon);
}
}
}
```
## API
### CouponCell Props
| Attribute | Description | Type | Default |
|------|------|------|------|
| title | Cell title | `String` | `Coupon` |
| chosen-coupon | Index of chosen coupon | `Number` | `-1` |
| coupons | Coupon list | `Array` | `[]` |
| editable | Cell editable | `Boolean` | `true` |
| border | Whether to show innner border | `Boolean` | `true` |
| currency | Currency symbol | `String` | `¥` |
### CouponList Props
| Attribute | Description | Type | Default |
|------|------|------|------|
| v-model | Current exchange code | `String` | - |
| chosen-coupon | Index of chosen coupon | `Number` | `-1` |
| coupons | Coupon list | `Array` | `[]` |
| disabled-coupons | Disabled coupon list | `Array` | `[]` |
| enabled-title | Title of coupon list | `String` | `Available` | - |
| disabled-title | Title of disabled coupon list | `String` | `Unavailable` | - |
| exchange-button-text | Exchange button text | `String` | `Exchange` |
| exchange-button-loading | Whether to show loading in exchange button | `Boolean` | `false` |
| exchange-button-disabled | Whether to disable exchange button | `Boolean` | `false` |
| exchange-min-length | Min length to enable exchange button | `Number` | `1` |
| displayed-coupon-index | Index of displayed coupon | `Number` | - |
| close-button-text | Close button text | `String` | `Close` |
| input-placeholder | Input placeholder | `String` | `Coupon code` |
| currency | Currency symbol | `String` | `¥` |
### CouponList Events
| Event | Description | Arguments |
|------|------|------|
| change | Triggered when change chosen coupon | index: index of chosen coupon |
| exchange | Triggered when exchange coupon | code: exchange code |
### Coupon Item Data Structure
| key | Description | Type |
|------|------|------|
| id | Id | `String` |
| name | Name | `String` |
| condition | Condition | `String` |
| startAt | Start time (Timestmap, unit second) | `Number` |
| endAt | End time (Timestmap, unit second) | `Number` |
| description | Description | `String` |
| reason | Unavailable reason | `String` |
| value | Value | `Number` |
| valueDesc | Value Text | `String` |
| unitDesc | Unit Text | `String` |
+215
View File
@@ -0,0 +1,215 @@
import { createNamespace } from '../utils';
import Tab from '../tab';
import Tabs from '../tabs';
import Field from '../field';
import Button from '../button';
import Coupon from '../coupon';
const [createComponent, bem, t] = createNamespace('coupon-list');
const EMPTY_IMAGE = 'https://img.yzcdn.cn/vant/coupon-empty.png';
export default createComponent({
model: {
prop: 'code'
},
props: {
code: String,
coupons: Array,
disabledCoupons: Array,
closeButtonText: String,
inputPlaceholder: String,
enabledTitle: String,
disabledTitle: String,
exchangeButtonText: String,
exchangeButtonLoading: Boolean,
exchangeButtonDisabled: Boolean,
exchangeMinLength: {
type: Number,
default: 1
},
chosenCoupon: {
type: Number,
default: -1
},
displayedCouponIndex: {
type: Number,
default: -1
},
showExchangeBar: {
type: Boolean,
default: true
},
showCloseButton: {
type: Boolean,
default: true
},
currency: {
type: String,
default: '¥'
}
},
data() {
return {
tab: 0,
winHeight: window.innerHeight,
currentCode: this.code || ''
};
},
computed: {
buttonDisabled() {
return (
!this.exchangeButtonLoading &&
(this.exchangeButtonDisabled ||
!this.currentCode ||
this.currentCode.length < this.exchangeMinLength)
);
},
listStyle() {
return {
height: this.winHeight - (this.showExchangeBar ? 140 : 94) + 'px'
};
}
},
watch: {
code(code) {
this.currentCode = code;
},
currentCode(code) {
this.$emit('input', code);
},
displayedCouponIndex(val) {
this.scrollToShowCoupon(val);
}
},
mounted() {
this.scrollToShowCoupon(this.displayedCouponIndex);
},
methods: {
onClickExchangeButton() {
this.$emit('exchange', this.currentCode);
// auto clear currentCode when not use vModel
if (!this.code) {
this.currentCode = '';
}
},
// scroll to show specific coupon
scrollToShowCoupon(index) {
if (index === -1) {
return;
}
this.$nextTick(() => {
const { card, list } = this.$refs;
/* istanbul ignore next */
if (list && card && card[index]) {
list.scrollTop = card[index].$el.offsetTop - 100;
}
});
},
renderEmpty() {
return (
<div class={bem('empty')}>
<img src={EMPTY_IMAGE} />
<p>{t('empty')}</p>
</div>
);
},
renderExchangeButton() {
return (
<Button
size="small"
type="danger"
class={bem('exchange')}
text={this.exchangeButtonText || t('exchange')}
loading={this.exchangeButtonLoading}
disabled={this.buttonDisabled}
onClick={this.onClickExchangeButton}
/>
);
}
},
render(h) {
const { coupons, disabledCoupons } = this;
const title = `${this.enabledTitle || t('enable')} (${coupons.length})`;
const disabledTitle = `${this.disabledTitle || t('disabled')} (${
disabledCoupons.length
})`;
const ExchangeBar = this.showExchangeBar && (
<Field
vModel={this.currentCode}
clearable
border={false}
class={bem('field')}
placeholder={this.inputPlaceholder || t('placeholder')}
maxlength="20"
scopedSlots={{
button: this.renderExchangeButton
}}
/>
);
const onChange = index => () => this.$emit('change', index);
const CouponTab = (
<Tab title={title}>
<div class={bem('list')} style={this.listStyle}>
{coupons.map((coupon, index) => (
<Coupon
ref="card"
key={coupon.id}
coupon={coupon}
currency={this.currency}
chosen={index === this.chosenCoupon}
nativeOnClick={onChange(index)}
/>
))}
{!coupons.length && this.renderEmpty()}
</div>
</Tab>
);
const DisabledCouponTab = (
<Tab title={disabledTitle}>
<div class={bem('list')} style={this.listStyle}>
{disabledCoupons.map(coupon => (
<Coupon disabled key={coupon.id} coupon={coupon} currency={this.currency} />
))}
{!disabledCoupons.length && this.renderEmpty()}
</div>
</Tab>
);
return (
<div class={bem()}>
{ExchangeBar}
<Tabs vModel={this.tab} class={bem('tab')} line-width={120}>
{CouponTab}
{DisabledCouponTab}
</Tabs>
<Button
vShow={this.showCloseButton}
size="large"
class={bem('close')}
text={this.closeButtonText || t('close')}
onClick={onChange(-1)}
/>
</div>
);
}
});
+47
View File
@@ -0,0 +1,47 @@
@import '../style/var';
.van-coupon-list {
position: relative;
height: 100%;
background-color: @coupon-list-background-color;
&__field {
padding: @coupon-list-field-padding;
}
&__exchange {
height: @coupon-list-exchange-button-height;
line-height: @coupon-list-exchange-button-height - 2px;
}
&__list {
box-sizing: border-box;
padding: 15px 0;
overflow-y: auto;
-webkit-overflow-scrolling: touch;
}
&__close {
position: absolute;
bottom: 0;
left: 0;
font-weight: 500;
}
&__empty {
padding-top: 60px;
text-align: center;
p {
margin: 15px 0;
color: @coupon-list-empty-tip-color;
font-size: @coupon-list-empty-tip-font-size;
line-height: @coupon-list-empty-tip-line-height;
}
img {
width: @coupon-list-empty-image-size;
height: @coupon-list-empty-image-size;
}
}
}
@@ -0,0 +1,14 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`renders demo correctly 1`] = `
<div>
<div>
<div class="van-cell van-cell--clickable van-coupon-cell">
<div class="van-cell__title"><span>优惠券</span></div>
<div class="van-cell__value"><span>2张可用</span></div><i class="van-icon van-icon-arrow van-cell__right-icon">
<!----></i>
</div>
<!---->
</div>
</div>
`;
@@ -0,0 +1,179 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`render coupon cell 1`] = `
<div class="van-cell van-cell--clickable van-coupon-cell">
<div class="van-cell__title"><span>优惠券</span></div>
<div class="van-cell__value"><span>使用优惠</span></div><i class="van-icon van-icon-arrow van-cell__right-icon">
<!----></i>
</div>
`;
exports[`render coupon cell with coupon 1`] = `
<div class="van-cell van-cell--clickable van-coupon-cell">
<div class="van-cell__title"><span>优惠券</span></div>
<div class="van-cell__value van-coupon-cell--selected"><span>-¥1.00</span></div><i class="van-icon van-icon-arrow van-cell__right-icon">
<!----></i>
</div>
`;
exports[`render coupon list 1`] = `
<div class="van-coupon-list">
<div class="van-cell van-cell--borderless van-field van-coupon-list__field">
<div class="van-cell__value van-cell__value--alone">
<div class="van-field__body"><input type="text" placeholder="请输入优惠码" maxlength="20" class="van-field__control">
<div class="van-field__button"><button disabled="disabled" class="van-button van-button--danger van-button--small van-button--disabled van-coupon-list__exchange"><span class="van-button__text">兑换</span></button></div>
</div>
</div>
</div>
<div class="van-tabs van-tabs--line van-coupon-list__tab">
<div class="van-tabs__wrap van-hairline--top-bottom">
<div role="tablist" class="van-tabs__nav van-tabs__nav--line">
<div role="tab" aria-selected="true" class="van-tab van-tab--active"><span class="van-ellipsis">可使用优惠券 (6)</span></div>
<div role="tab" class="van-tab"><span class="van-ellipsis">不可使用优惠券 (2)</span></div>
<div class="van-tabs__line"></div>
</div>
</div>
<div class="van-tabs__content">
<div role="tabpanel" class="van-tab__pane">
<div class="van-coupon-list__list" style="height: 628px;">
<div class="van-coupon">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount"></h2>
<p>无使用门槛</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name"></h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
</div>
</div>
</div>
<div class="van-coupon">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount"><span>¥</span> 1.5</h2>
<p>无使用门槛</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name">name</h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
<div role="checkbox" tabindex="0" aria-checked="true" class="van-checkbox van-coupon__corner">
<div class="van-checkbox__icon van-checkbox__icon--round van-checkbox__icon--checked"><i class="van-icon van-icon-success" style="border-color: #f44; background-color: rgb(255, 68, 68);">
<!----></i></div>
</div>
</div>
</div>
<p class="van-coupon__description">description</p>
</div>
<div class="van-coupon">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount"><span>¥</span> 1</h2>
<p>无使用门槛</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name">name</h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
</div>
</div>
<p class="van-coupon__description">description</p>
</div>
<div class="van-coupon">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount"><span>¥</span> 1.23</h2>
<p>无使用门槛</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name">name</h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
</div>
</div>
<p class="van-coupon__description">description</p>
</div>
<div class="van-coupon">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount">8.8折</h2>
<p>满0.5元可用</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name">name</h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
</div>
</div>
</div>
<div class="van-coupon">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount">9折</h2>
<p>满0.5元可用</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name">name</h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
</div>
</div>
</div>
</div>
</div>
<div role="tabpanel" class="van-tab__pane" style="display: none;">
<!---->
</div>
</div>
</div><button class="van-button van-button--default van-button--large van-coupon-list__close"><span class="van-button__text">不使用优惠</span></button>
</div>
`;
exports[`render disabled coupon 1`] = `
<div class="van-coupon van-coupon--disabled">
<div class="van-coupon__content">
<div class="van-coupon__head">
<h2 class="van-coupon__amount"><span>¥</span> 1.5</h2>
<p>无使用门槛</p>
</div>
<div class="van-coupon__body">
<h2 class="van-coupon__name">name</h2>
<p>有效期:2017.03.10 - 2017.12.30</p>
</div>
</div>
<p class="van-coupon__description">reason</p>
</div>
`;
exports[`render empty coupon list 1`] = `
<div class="van-coupon-list">
<div class="van-cell van-cell--borderless van-field van-coupon-list__field">
<div class="van-cell__value van-cell__value--alone">
<div class="van-field__body"><input type="text" placeholder="请输入优惠码" maxlength="20" class="van-field__control">
<div class="van-field__button"><button disabled="disabled" class="van-button van-button--danger van-button--small van-button--disabled van-coupon-list__exchange"><span class="van-button__text">兑换</span></button></div>
</div>
</div>
</div>
<div class="van-tabs van-tabs--line van-coupon-list__tab">
<div class="van-tabs__wrap van-hairline--top-bottom">
<div role="tablist" class="van-tabs__nav van-tabs__nav--line">
<div role="tab" class="van-tab"><span class="van-ellipsis">可使用优惠券 (0)</span></div>
<div role="tab" class="van-tab van-tab--active" aria-selected="true"><span class="van-ellipsis">不可使用优惠券 (0)</span></div>
<div class="van-tabs__line"></div>
</div>
</div>
<div class="van-tabs__content">
<div role="tabpanel" class="van-tab__pane" style="display: none;">
<div class="van-coupon-list__list" style="height: 628px;">
<div class="van-coupon-list__empty"><img src="https://img.yzcdn.cn/vant/coupon-empty.png">
<p>暂无优惠券</p>
</div>
</div>
</div>
<div role="tabpanel" class="van-tab__pane" style="">
<div class="van-coupon-list__list" style="height: 628px;">
<div class="van-coupon-list__empty"><img src="https://img.yzcdn.cn/vant/coupon-empty.png">
<p>暂无优惠券</p>
</div>
</div>
</div>
</div>
</div><button class="van-button van-button--default van-button--large van-coupon-list__close"><span class="van-button__text">不使用优惠</span></button>
</div>
`;
+4
View File
@@ -0,0 +1,4 @@
import Demo from '../demo';
import demoTest from '../../../test/demo-test';
demoTest(Demo);
+147
View File
@@ -0,0 +1,147 @@
import Coupon from '../../coupon';
import CouponList from '..';
import CouponCell from '../../coupon-cell';
import { later, mount } from '../../../test/utils';
const coupon = {
id: 1,
discount: 0,
denominations: 150,
originCondition: 0,
reason: '',
value: 150,
name: 'name',
description: 'description',
startAt: 1489104000,
endAt: 1514592000
};
const coupon2 = {
...coupon,
denominations: 100
};
const coupon3 = {
...coupon,
denominations: 123
};
const emptyCoupon = {
id: 0,
discount: 0,
denominations: 0,
originCondition: 0,
startAt: 1489104000,
endAt: 1514592000
};
const discountCoupon = {
...coupon,
id: 2,
discount: 88,
denominations: 0,
originCondition: 50,
value: 12,
description: ''
};
const discountCoupon2 = {
...coupon,
id: 2,
discount: 90,
denominations: 0,
originCondition: 50,
value: 12,
description: ''
};
const disabledCoupon = {
...coupon,
id: 3,
reason: 'reason'
};
const disabledDiscountCoupon = {
...discountCoupon,
discount: 10,
id: 4,
reason: ''
};
test('render disabled coupon', () => {
const wrapper = mount(Coupon, {
propsData: {
coupon: disabledCoupon,
disabled: true
}
});
expect(wrapper).toMatchSnapshot();
});
test('render coupon list', async () => {
const wrapper = mount(CouponList, {
propsData: {
chosenCoupon: 1,
coupons: [emptyCoupon, coupon, coupon2, coupon3, discountCoupon, discountCoupon2],
disabledCoupons: [disabledCoupon, disabledDiscountCoupon]
}
});
await later();
expect(wrapper).toMatchSnapshot();
});
test('render empty coupon list', () => {
const wrapper = mount(CouponList, {
propsData: {
coupons: [],
disabledCoupons: []
}
});
wrapper.findAll('.van-tab').at(1).trigger('click');
expect(wrapper).toMatchSnapshot();
});
test('exchange coupon', () => {
const wrapper = mount(CouponList);
const exchange = wrapper.find('.van-coupon-list__exchange');
wrapper.setData({
currentCode: '1',
displayedCouponIndex: 1
});
exchange.trigger('click');
wrapper.setProps({ code: '2' });
exchange.trigger('click');
expect(wrapper.emitted('exchange')[0][0]).toBe('1');
expect(wrapper.emitted('exchange')[1][0]).toBe('2');
expect(wrapper.emitted('input')[0][0]).toBe('1');
expect(wrapper.emitted('input')[1][0]).toBe('');
expect(wrapper.emitted('input')[2][0]).toBe('2');
});
test('render coupon cell', () => {
const onClick = jest.fn();
const wrapper = mount(CouponCell, {
context: {
on: {
click: onClick
}
}
});
expect(wrapper).toMatchSnapshot();
wrapper.trigger('click');
expect(onClick).toHaveBeenCalledTimes(1);
});
test('render coupon cell with coupon', () => {
const wrapper = mount(CouponCell, {
propsData: {
coupons: [{ value: 100 }],
chosenCoupon: 0
}
});
expect(wrapper).toMatchSnapshot();
});
+123
View File
@@ -0,0 +1,123 @@
# Coupon 优惠券选择器
### 引入
``` javascript
import { CouponCell, CouponList } from 'vant';
Vue.use(CouponCell).use(CouponList);
```
## 代码演示
### 基础用法
```html
<!-- 优惠券单元格 -->
<van-coupon-cell
:coupons="coupons"
:chosen-coupon="chosenCoupon"
@click="showList = true"
/>
<!-- 优惠券列表 -->
<van-popup v-model="showList" position="bottom">
<van-coupon-list
:coupons="coupons"
:chosen-coupon="chosenCoupon"
:disabled-coupons="disabledCoupons"
@change="onChange"
@exchange="onExchange"
/>
</van-popup>
```
```javascript
const coupon = {
available: 1,
condition: '无使用门槛\n最多优惠12元',
reason: '',
value: 150,
name: '优惠券名称',
startAt: 1489104000,
endAt: 1514592000,
valueDesc: '1.5',
unitDesc: '元'
};
export default {
data() {
return {
chosenCoupon: -1,
coupons: [coupon],
disabledCoupons: [coupon]
}
},
methods: {
onChange(index) {
this.showList = false;
this.chosenCoupon = index;
},
onExchange(code) {
this.coupons.push(coupon);
}
}
}
```
## API
### CouponCell Props
| 参数 | 说明 | 类型 | 默认值 | 版本 |
|------|------|------|------|------|
| title | 单元格标题 | `String` | `优惠券` | - |
| chosen-coupon | 当前选中优惠券的索引 | `Number` | `-1` | - |
| coupons | 可用优惠券列表 | `Array` | `[]` | - |
| editable | 能否切换优惠券 | `Boolean` | `true` | - |
| border | 是否显示内边框 | `Boolean` | `true` | 1.3.10 |
| currency | 货币符号 | `String` | `¥` | - | 1.5.0 |
### CouponList Props
| 参数 | 说明 | 类型 | 默认值 | 版本 |
|------|------|------|------|------|
| v-model | 当前输入的兑换码 | `String` | - | - |
| chosen-coupon | 当前选中优惠券的索引 | `Number` | `-1` | - |
| coupons | 可用优惠券列表 | `Array` | `[]` | - |
| disabled-coupons | 不可用优惠券列表 | `Array` | `[]` | - |
| enabled-title | 可用优惠券列表标题 | `String` | `可使用优惠券` | - |
| disabled-title | 不可用优惠券列表标题 | `String` | `不可使用优惠券` | - |
| exchange-button-text | 兑换按钮文字 | `String` | `兑换` | - |
| exchange-button-loading | 是否显示兑换按钮加载动画 | `Boolean` | `false` | - |
| exchange-button-disabled | 是否禁用兑换按钮 | `Boolean` | `false` | - |
| exchange-min-length | 兑换码最小长度 | `Number` | `1` | - |
| displayed-coupon-index | 滚动至特定优惠券位置 | `Number` | - | - |
| show-close-button | 是否显示列表底部按钮 | `Boolean` | `true` | - |
| close-button-text | 列表底部按钮文字 | `String` | `不使用优惠` | - |
| input-placeholder | 输入框文字提示 | `String` | `请输入优惠码` | - |
| show-exchange-bar | 是否展示兑换栏 | `Boolean` | `true` | - |
| currency | 货币符号 | `String` | `¥` | - | 1.5.0 |
### CouponList Events
| 事件名 | 说明 | 回调参数 |
|------|------|------|
| change | 优惠券切换回调 | index, 选中优惠券的索引 |
| exchange | 兑换优惠券回调 | code, 兑换码 |
### 优惠券字段说明
| key | 说明 | 类型 |
|------|------|------|
| id | 优惠券 id | `String` |
| name | 优惠券名称 | `String` |
| condition | 满减条件 | `String` |
| startAt | 卡有效开始时间 (时间戳, 单位秒) | `Number` |
| endAt | 卡失效日期 (时间戳, 单位秒) | `Number` |
| description | 描述信息,优惠券可用时展示 | `String` |
| reason | 不可用原因,优惠券不可用时展示 | `String` |
| value | 折扣券优惠金额,单位分 | `Number` |
| valueDesc | 折扣券优惠金额文案 | `String` |
| unitDesc | 单位文案 | `String` |