@gitlab/ui 37.4.2 → 37.5.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +26 -0
- package/dist/components/base/accordion/accordion_item.js +14 -1
- package/dist/components/base/datepicker/datepicker.documentation.js +2 -47
- package/dist/components/base/datepicker/datepicker.js +37 -1
- package/dist/components/base/dropdown/dropdown.js +2 -2
- package/dist/components/base/filtered_search/filtered_search.js +24 -8
- package/dist/components/base/filtered_search/filtered_search_term.js +10 -1
- package/dist/components/base/filtered_search/filtered_search_utils.js +2 -1
- package/dist/index.css +1 -1
- package/dist/index.css.map +1 -1
- package/documentation/documented_stories.js +1 -0
- package/package.json +2 -2
- package/src/components/base/accordion/accordion_item.spec.js +12 -0
- package/src/components/base/accordion/accordion_item.stories.js +4 -2
- package/src/components/base/accordion/accordion_item.vue +12 -1
- package/src/components/base/datepicker/datepicker.documentation.js +0 -59
- package/src/components/base/datepicker/datepicker.md +0 -6
- package/src/components/base/datepicker/datepicker.stories.js +97 -71
- package/src/components/base/datepicker/datepicker.vue +36 -1
- package/src/components/base/dropdown/dropdown.spec.js +29 -0
- package/src/components/base/dropdown/dropdown.stories.js +4 -1
- package/src/components/base/dropdown/dropdown.vue +5 -3
- package/src/components/base/dropdown/dropdown_section_header.scss +1 -0
- package/src/components/base/filtered_search/filtered_search.spec.js +106 -12
- package/src/components/base/filtered_search/filtered_search.stories.js +3 -0
- package/src/components/base/filtered_search/filtered_search.vue +21 -6
- package/src/components/base/filtered_search/filtered_search_term.spec.js +14 -9
- package/src/components/base/filtered_search/filtered_search_term.vue +7 -1
- package/src/components/base/filtered_search/filtered_search_utils.js +2 -0
- package/dist/components/base/datepicker/examples/datepicker.basic.example.js +0 -48
- package/dist/components/base/datepicker/examples/datepicker.custom_input.example.js +0 -48
- package/dist/components/base/datepicker/examples/datepicker.disabled.example.js +0 -48
- package/dist/components/base/datepicker/examples/datepicker.open_on_focus.example.js +0 -48
- package/dist/components/base/datepicker/examples/datepicker.with_clear_button.example.js +0 -48
- package/dist/components/base/datepicker/examples/index.js +0 -32
- package/src/components/base/datepicker/examples/datepicker.basic.example.vue +0 -12
- package/src/components/base/datepicker/examples/datepicker.custom_input.example.vue +0 -21
- package/src/components/base/datepicker/examples/datepicker.disabled.example.vue +0 -12
- package/src/components/base/datepicker/examples/datepicker.open_on_focus.example.vue +0 -12
- package/src/components/base/datepicker/examples/datepicker.with_clear_button.example.vue +0 -12
- package/src/components/base/datepicker/examples/index.js +0 -38
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@gitlab/ui",
|
|
3
|
-
"version": "37.
|
|
3
|
+
"version": "37.5.2",
|
|
4
4
|
"description": "GitLab UI Components",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -83,7 +83,7 @@
|
|
|
83
83
|
"@arkweid/lefthook": "^0.7.6",
|
|
84
84
|
"@babel/core": "^7.10.2",
|
|
85
85
|
"@babel/preset-env": "^7.10.2",
|
|
86
|
-
"@gitlab/eslint-plugin": "
|
|
86
|
+
"@gitlab/eslint-plugin": "11.0.0",
|
|
87
87
|
"@gitlab/stylelint-config": "4.0.0",
|
|
88
88
|
"@gitlab/svgs": "2.6.0",
|
|
89
89
|
"@rollup/plugin-commonjs": "^11.1.0",
|
|
@@ -8,6 +8,7 @@ import GlAccordionItem from './accordion_item.vue';
|
|
|
8
8
|
describe('GlAccordionItem', () => {
|
|
9
9
|
let wrapper;
|
|
10
10
|
const defaultTitle = 'Item 1';
|
|
11
|
+
const titleVisible = 'Item 1 visible';
|
|
11
12
|
const defaultSlot = 'Hello';
|
|
12
13
|
|
|
13
14
|
const createComponent = (props = {}, { defaultHeaderLevel = 3, accordionSetId = false } = {}) => {
|
|
@@ -38,6 +39,17 @@ describe('GlAccordionItem', () => {
|
|
|
38
39
|
expect(findButton().find('span').text()).toBe(defaultTitle);
|
|
39
40
|
});
|
|
40
41
|
|
|
42
|
+
it('renders alternative button text when the content is visible and the titleVisible property is set', async () => {
|
|
43
|
+
createComponent({ titleVisible });
|
|
44
|
+
|
|
45
|
+
expect(findButton().find('span').text()).toBe(defaultTitle);
|
|
46
|
+
|
|
47
|
+
await waitForAnimationFrame();
|
|
48
|
+
await findButton().trigger('click');
|
|
49
|
+
|
|
50
|
+
expect(findButton().find('span').text()).toBe(titleVisible);
|
|
51
|
+
});
|
|
52
|
+
|
|
41
53
|
it('renders the appropriate header element', () => {
|
|
42
54
|
createComponent({}, { defaultHeaderLevel: 3 });
|
|
43
55
|
|
|
@@ -2,7 +2,7 @@ import readme from './accordion_item.md';
|
|
|
2
2
|
import GlAccordionItem from './accordion_item.vue';
|
|
3
3
|
|
|
4
4
|
const template = `
|
|
5
|
-
<gl-accordion-item :title="title" :visible="visible" :header-level="headerLevel">
|
|
5
|
+
<gl-accordion-item :title="title" :titleVisible="titleVisible" :visible="visible" :header-level="headerLevel">
|
|
6
6
|
Lorem ipsum dolor sit amet consectetur adipisicing elit. Delectus, maiores.
|
|
7
7
|
</gl-accordion-item>
|
|
8
8
|
`;
|
|
@@ -13,10 +13,12 @@ const generateProps = ({
|
|
|
13
13
|
visible = defaultValue('visible'),
|
|
14
14
|
headerLevel = 3,
|
|
15
15
|
title = 'Accordion Item Title',
|
|
16
|
+
titleVisible = undefined,
|
|
16
17
|
} = {}) => ({
|
|
17
18
|
visible,
|
|
18
19
|
headerLevel,
|
|
19
20
|
title,
|
|
21
|
+
titleVisible,
|
|
20
22
|
});
|
|
21
23
|
|
|
22
24
|
const Template = (args) => ({
|
|
@@ -32,7 +34,7 @@ const Template = (args) => ({
|
|
|
32
34
|
});
|
|
33
35
|
|
|
34
36
|
export const Default = Template.bind({});
|
|
35
|
-
Default.args = generateProps();
|
|
37
|
+
Default.args = generateProps({ titleVisible: 'Accordion Item Title Expanded' });
|
|
36
38
|
|
|
37
39
|
export const InitiallyExpanded = Template.bind({});
|
|
38
40
|
InitiallyExpanded.args = generateProps({ visible: true, title: 'Item Content Initially Expanded' });
|
|
@@ -24,6 +24,14 @@ export default {
|
|
|
24
24
|
required: true,
|
|
25
25
|
},
|
|
26
26
|
/*
|
|
27
|
+
Used to set the title of accordion link when the content is visible
|
|
28
|
+
*/
|
|
29
|
+
titleVisible: {
|
|
30
|
+
type: String,
|
|
31
|
+
default: null,
|
|
32
|
+
required: false,
|
|
33
|
+
},
|
|
34
|
+
/*
|
|
27
35
|
When set, it will ensure the accordion item is initially visible
|
|
28
36
|
*/
|
|
29
37
|
visible: {
|
|
@@ -60,6 +68,9 @@ When set, it will ensure the accordion item is initially visible
|
|
|
60
68
|
icon() {
|
|
61
69
|
return this.isVisible ? 'chevron-down' : 'chevron-right';
|
|
62
70
|
},
|
|
71
|
+
buttonTitle() {
|
|
72
|
+
return this.isVisible && this.titleVisible ? this.titleVisible : this.title;
|
|
73
|
+
},
|
|
63
74
|
},
|
|
64
75
|
};
|
|
65
76
|
</script>
|
|
@@ -73,7 +84,7 @@ When set, it will ensure the accordion item is initially visible
|
|
|
73
84
|
button-text-classes="gl-display-flex"
|
|
74
85
|
:icon="icon"
|
|
75
86
|
>
|
|
76
|
-
{{
|
|
87
|
+
{{ buttonTitle }}
|
|
77
88
|
</gl-button>
|
|
78
89
|
</component>
|
|
79
90
|
<b-collapse
|
|
@@ -1,64 +1,5 @@
|
|
|
1
1
|
import description from './datepicker.md';
|
|
2
|
-
import examples from './examples';
|
|
3
2
|
|
|
4
3
|
export default {
|
|
5
4
|
description,
|
|
6
|
-
examples,
|
|
7
|
-
propsInfo: {
|
|
8
|
-
target: {
|
|
9
|
-
additionalInfo:
|
|
10
|
-
'Selector of element that triggers the datepicker. Defaults to the calendar icon. Pass `null` to trigger on input focus.',
|
|
11
|
-
},
|
|
12
|
-
container: {
|
|
13
|
-
additionalInfo:
|
|
14
|
-
'DOM node to render calendar into. Defaults to the datepicker container. Pass `null` to use Pikaday default.',
|
|
15
|
-
},
|
|
16
|
-
disableDayFn: {
|
|
17
|
-
additionalInfo:
|
|
18
|
-
'Accepts a function that accepts a date as argument and returns true if the date is disabled.',
|
|
19
|
-
},
|
|
20
|
-
autocomplete: {
|
|
21
|
-
additionalInfo:
|
|
22
|
-
'Defaults to `off` when datepicker opens on focus, otherwise defaults to `null`.',
|
|
23
|
-
},
|
|
24
|
-
defaultDate: {
|
|
25
|
-
additionalInfo: 'Use this prop to set the initial date for the datepicker.',
|
|
26
|
-
},
|
|
27
|
-
},
|
|
28
|
-
events: [
|
|
29
|
-
{
|
|
30
|
-
event: 'input',
|
|
31
|
-
description: 'Emitted when a new date has been selected.',
|
|
32
|
-
args: [
|
|
33
|
-
{
|
|
34
|
-
arg: 'date',
|
|
35
|
-
description: 'The selected date',
|
|
36
|
-
},
|
|
37
|
-
],
|
|
38
|
-
},
|
|
39
|
-
{
|
|
40
|
-
event: 'close',
|
|
41
|
-
description: 'Emitted when the datepicker is hidden.',
|
|
42
|
-
},
|
|
43
|
-
{
|
|
44
|
-
event: 'open',
|
|
45
|
-
description: 'Emitted when the datepicker becomes visible.',
|
|
46
|
-
},
|
|
47
|
-
{
|
|
48
|
-
event: 'draw',
|
|
49
|
-
description: 'Emitted when the datepicker draws a new month.',
|
|
50
|
-
},
|
|
51
|
-
{
|
|
52
|
-
event: 'clear',
|
|
53
|
-
description: 'Emitted when the clear button is clicked.',
|
|
54
|
-
},
|
|
55
|
-
],
|
|
56
|
-
slots: [
|
|
57
|
-
{
|
|
58
|
-
name: 'default',
|
|
59
|
-
description:
|
|
60
|
-
'(optional) Input to display and bind the datepicker to. Defaults to `<gl-form-input />`',
|
|
61
|
-
scopedProps: `{ formattedDate: string }`,
|
|
62
|
-
},
|
|
63
|
-
],
|
|
64
5
|
};
|
|
@@ -1,84 +1,110 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
1
|
+
import { GlDatepicker } from '../../../index';
|
|
2
|
+
import { disableControls } from '../../../utils/stories_utils';
|
|
3
3
|
import { useFakeDate } from '../../../utils/use_fake_date';
|
|
4
4
|
import readme from './datepicker.md';
|
|
5
|
-
import GlDatepicker from './datepicker.vue';
|
|
6
5
|
|
|
7
|
-
const
|
|
6
|
+
const defaults = {
|
|
7
|
+
components: { GlDatepicker },
|
|
8
|
+
mixins: [useFakeDate()],
|
|
9
|
+
};
|
|
8
10
|
|
|
11
|
+
const currentYear = 2020;
|
|
9
12
|
const defaultDate = new Date(currentYear, 0, 15);
|
|
10
13
|
const defaultMinDate = new Date(currentYear, 0, 1);
|
|
11
14
|
const defaultMaxDate = new Date(currentYear, 2, 31);
|
|
12
15
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
+
const generateProps = ({ minDate = defaultMinDate, maxDate = defaultMaxDate } = {}) => ({
|
|
17
|
+
minDate,
|
|
18
|
+
maxDate,
|
|
19
|
+
});
|
|
16
20
|
|
|
17
|
-
|
|
18
|
-
return {
|
|
19
|
-
minDate: {
|
|
20
|
-
type: Date,
|
|
21
|
-
default: dateTypeKnob('minDate', defaultMinDate),
|
|
22
|
-
},
|
|
23
|
-
maxDate: {
|
|
24
|
-
type: Date,
|
|
25
|
-
default: dateTypeKnob('maxDate', defaultMaxDate),
|
|
26
|
-
},
|
|
27
|
-
};
|
|
28
|
-
}
|
|
21
|
+
const wrap = (template) => `<div style="height: 280px">${template}</div>`;
|
|
29
22
|
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
.
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
23
|
+
export const Default = (_args, { argTypes }) => ({
|
|
24
|
+
...defaults,
|
|
25
|
+
props: Object.keys(argTypes),
|
|
26
|
+
data() {
|
|
27
|
+
return {
|
|
28
|
+
pickerValue: defaultDate,
|
|
29
|
+
};
|
|
30
|
+
},
|
|
31
|
+
template: wrap(`
|
|
32
|
+
<gl-datepicker :max-date="maxDate" :min-date="minDate" :start-opened="true" v-model="pickerValue" />
|
|
33
|
+
`),
|
|
34
|
+
});
|
|
35
|
+
Default.args = generateProps();
|
|
36
|
+
|
|
37
|
+
export const CustomTrigger = (_args, { argTypes }) => ({
|
|
38
|
+
...defaults,
|
|
39
|
+
props: Object.keys(argTypes),
|
|
40
|
+
data() {
|
|
41
|
+
return {
|
|
42
|
+
pickerValue: null,
|
|
43
|
+
};
|
|
44
|
+
},
|
|
45
|
+
template: wrap(`
|
|
46
|
+
<div class="dropdown">
|
|
47
|
+
<button type="button" class="dropdown-menu-toggle">
|
|
48
|
+
<span class="dropdown-toggle-text"> Start date: {{value}} </span>
|
|
49
|
+
</button>
|
|
50
|
+
</div>
|
|
51
|
+
<gl-datepicker v-model="pickerValue" target=".dropdown-menu-toggle" :container="null" />
|
|
52
|
+
`),
|
|
53
|
+
});
|
|
54
|
+
CustomTrigger.args = generateProps();
|
|
55
|
+
|
|
56
|
+
export const WithClearButton = (_args, { argTypes }) => ({
|
|
57
|
+
...defaults,
|
|
58
|
+
props: Object.keys(argTypes),
|
|
59
|
+
data() {
|
|
60
|
+
return {
|
|
61
|
+
pickerValue: defaultDate,
|
|
62
|
+
};
|
|
63
|
+
},
|
|
64
|
+
template: wrap(`
|
|
65
|
+
<gl-datepicker showClearButton :max-date="maxDate" :min-date="minDate" v-model="pickerValue" />
|
|
66
|
+
`),
|
|
67
|
+
});
|
|
68
|
+
WithClearButton.args = generateProps();
|
|
69
|
+
|
|
70
|
+
export default {
|
|
71
|
+
title: 'base/datepicker',
|
|
72
|
+
component: GlDatepicker,
|
|
73
|
+
parameters: {
|
|
74
|
+
docs: {
|
|
75
|
+
description: {
|
|
76
|
+
component: readme,
|
|
77
|
+
},
|
|
57
78
|
},
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
79
|
+
},
|
|
80
|
+
argTypes: {
|
|
81
|
+
...disableControls([
|
|
82
|
+
'target',
|
|
83
|
+
'container',
|
|
84
|
+
'value',
|
|
85
|
+
'startRange',
|
|
86
|
+
'endRange',
|
|
87
|
+
'disableDayFn',
|
|
88
|
+
'firstDay',
|
|
89
|
+
'arialLabel',
|
|
90
|
+
'placeholder',
|
|
91
|
+
'autocomplete',
|
|
92
|
+
'disabled',
|
|
93
|
+
'displayField',
|
|
94
|
+
'startOpened',
|
|
95
|
+
'defaultDate',
|
|
96
|
+
'i18n',
|
|
97
|
+
'theme',
|
|
98
|
+
'showClearButton',
|
|
99
|
+
'inputId',
|
|
100
|
+
'inputLabel',
|
|
101
|
+
'inputName',
|
|
102
|
+
]),
|
|
103
|
+
minDate: {
|
|
104
|
+
control: { type: 'date' },
|
|
73
105
|
},
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
return {
|
|
77
|
-
value: defaultDate,
|
|
78
|
-
};
|
|
106
|
+
maxDate: {
|
|
107
|
+
control: { type: 'date' },
|
|
79
108
|
},
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
</gl-datepicker>
|
|
83
|
-
`,
|
|
84
|
-
}));
|
|
109
|
+
},
|
|
110
|
+
};
|
|
@@ -45,11 +45,17 @@ export default {
|
|
|
45
45
|
GlButton,
|
|
46
46
|
},
|
|
47
47
|
props: {
|
|
48
|
+
/**
|
|
49
|
+
* Selector of element that triggers the datepicker. Defaults to the calendar icon. Pass `null` to trigger on input focus.
|
|
50
|
+
*/
|
|
48
51
|
target: {
|
|
49
52
|
type: String,
|
|
50
53
|
required: false,
|
|
51
54
|
default: '',
|
|
52
55
|
},
|
|
56
|
+
/**
|
|
57
|
+
* DOM node to render calendar into. Defaults to the datepicker container. Pass `null` to use Pikaday default.
|
|
58
|
+
*/
|
|
53
59
|
container: {
|
|
54
60
|
type: String,
|
|
55
61
|
required: false,
|
|
@@ -80,6 +86,9 @@ export default {
|
|
|
80
86
|
required: false,
|
|
81
87
|
default: null,
|
|
82
88
|
},
|
|
89
|
+
/**
|
|
90
|
+
* Accepts a function that accepts a date as argument and returns true if the date is disabled.
|
|
91
|
+
*/
|
|
83
92
|
disableDayFn: {
|
|
84
93
|
type: Function,
|
|
85
94
|
required: false,
|
|
@@ -100,6 +109,9 @@ export default {
|
|
|
100
109
|
required: false,
|
|
101
110
|
default: defaultDateFormat,
|
|
102
111
|
},
|
|
112
|
+
/**
|
|
113
|
+
* Defaults to `off` when datepicker opens on focus, otherwise defaults to `null`.
|
|
114
|
+
*/
|
|
103
115
|
autocomplete: {
|
|
104
116
|
type: String,
|
|
105
117
|
required: false,
|
|
@@ -120,6 +132,9 @@ export default {
|
|
|
120
132
|
required: false,
|
|
121
133
|
default: false,
|
|
122
134
|
},
|
|
135
|
+
/**
|
|
136
|
+
* Use this prop to set the initial date for the datepicker.
|
|
137
|
+
*/
|
|
123
138
|
defaultDate: {
|
|
124
139
|
type: Date,
|
|
125
140
|
required: false,
|
|
@@ -274,19 +289,35 @@ export default {
|
|
|
274
289
|
},
|
|
275
290
|
methods: {
|
|
276
291
|
selected(date) {
|
|
292
|
+
/**
|
|
293
|
+
* Emitted when a new date has been selected.
|
|
294
|
+
* @property {Date} date The selected date
|
|
295
|
+
*/
|
|
277
296
|
this.$emit('input', date);
|
|
278
297
|
},
|
|
279
298
|
closed() {
|
|
299
|
+
/**
|
|
300
|
+
* Emitted when the datepicker is hidden.
|
|
301
|
+
*/
|
|
280
302
|
this.$emit('close');
|
|
281
303
|
},
|
|
282
304
|
opened() {
|
|
305
|
+
/**
|
|
306
|
+
* Emitted when the datepicker becomes visible.
|
|
307
|
+
*/
|
|
283
308
|
this.$emit('open');
|
|
284
309
|
},
|
|
285
310
|
cleared() {
|
|
286
311
|
this.textInput = '';
|
|
312
|
+
/**
|
|
313
|
+
* Emitted when the clear button is clicked.
|
|
314
|
+
*/
|
|
287
315
|
this.$emit('clear');
|
|
288
316
|
},
|
|
289
317
|
draw() {
|
|
318
|
+
/**
|
|
319
|
+
* Emitted when the datepicker draws a new month.
|
|
320
|
+
*/
|
|
290
321
|
this.$emit('monthChange');
|
|
291
322
|
},
|
|
292
323
|
onKeydown() {
|
|
@@ -302,7 +333,11 @@ export default {
|
|
|
302
333
|
|
|
303
334
|
<template>
|
|
304
335
|
<div class="gl-datepicker d-inline-block">
|
|
305
|
-
<div v-if="showDefaultField" class="
|
|
336
|
+
<div v-if="showDefaultField" class="gl-relative">
|
|
337
|
+
<!--
|
|
338
|
+
@slot (optional) Input to display and bind the datepicker to. Defaults to `<gl-form-input />`
|
|
339
|
+
@binding {string} formattedDate
|
|
340
|
+
-->
|
|
306
341
|
<slot :formatted-date="formattedDate">
|
|
307
342
|
<gl-form-input
|
|
308
343
|
:id="inputId"
|
|
@@ -336,6 +336,7 @@ describe('new dropdown', () => {
|
|
|
336
336
|
const slots = { 'button-text': mockComponent };
|
|
337
337
|
buildWrapper({ loading: true, icon: 'close' }, slots);
|
|
338
338
|
expect(wrapper.findComponent(mockComponent).exists()).toBe(true);
|
|
339
|
+
expect(wrapper.text()).toBe('mock');
|
|
339
340
|
expect(findLoadingIcon().exists()).toBe(true);
|
|
340
341
|
expect(findIcon().exists()).toBe(true);
|
|
341
342
|
expect(findCaret().exists()).toBe(true);
|
|
@@ -345,12 +346,40 @@ describe('new dropdown', () => {
|
|
|
345
346
|
const slots = { 'button-content': mockComponent };
|
|
346
347
|
buildWrapper({ loading: true, icon: 'close' }, slots);
|
|
347
348
|
expect(wrapper.findComponent(mockComponent).exists()).toBe(true);
|
|
349
|
+
expect(wrapper.text()).toBe('mock');
|
|
348
350
|
expect(findLoadingIcon().exists()).toBe(false);
|
|
349
351
|
expect(findIcon().exists()).toBe(false);
|
|
350
352
|
expect(findCaret().exists()).toBe(false);
|
|
351
353
|
});
|
|
352
354
|
});
|
|
353
355
|
|
|
356
|
+
describe('icon only dropdown', () => {
|
|
357
|
+
it('shows the icon and dropdown caret', () => {
|
|
358
|
+
buildWrapper({ icon: 'paper-airplane' });
|
|
359
|
+
expect(wrapper.text()).toBe('');
|
|
360
|
+
expect(findLoadingIcon().exists()).toBe(false);
|
|
361
|
+
expect(findIcon().exists()).toBe(true);
|
|
362
|
+
expect(findCaret().exists()).toBe(true);
|
|
363
|
+
});
|
|
364
|
+
|
|
365
|
+
it('shows text for screen readers', () => {
|
|
366
|
+
buildWrapper({ icon: 'paper-airplane', text: 'screenreader button text', textSrOnly: true });
|
|
367
|
+
expect(wrapper.text()).toBe('screenreader button text');
|
|
368
|
+
expect(wrapper.find('span').classes()).toContain('gl-sr-only');
|
|
369
|
+
expect(findLoadingIcon().exists()).toBe(false);
|
|
370
|
+
expect(findIcon().exists()).toBe(true);
|
|
371
|
+
expect(findCaret().exists()).toBe(true);
|
|
372
|
+
});
|
|
373
|
+
|
|
374
|
+
it('shows loading spinner instead of icon when loading', () => {
|
|
375
|
+
buildWrapper({ icon: 'paper-airplane', loading: true });
|
|
376
|
+
expect(wrapper.text()).toBe('');
|
|
377
|
+
expect(findLoadingIcon().exists()).toBe(true);
|
|
378
|
+
expect(findIcon().exists()).toBe(false);
|
|
379
|
+
expect(findCaret().exists()).toBe(true);
|
|
380
|
+
});
|
|
381
|
+
});
|
|
382
|
+
|
|
354
383
|
describe('Clear all button', () => {
|
|
355
384
|
it('is not visible by default', () => {
|
|
356
385
|
buildWrapper({});
|
|
@@ -274,7 +274,10 @@ documentedStoriesOf('base/dropdown', readme)
|
|
|
274
274
|
template: wrap`
|
|
275
275
|
<gl-dropdown-section-header>Header title</gl-dropdown-section-header>
|
|
276
276
|
<gl-dropdown-item>First item</gl-dropdown-item>
|
|
277
|
-
<gl-dropdown-item>Second item</gl-dropdown-item
|
|
277
|
+
<gl-dropdown-item>Second item</gl-dropdown-item>
|
|
278
|
+
<gl-dropdown-section-header>I am a really long header title which should wrap</gl-dropdown-section-header>
|
|
279
|
+
<gl-dropdown-item>Third item</gl-dropdown-item>
|
|
280
|
+
<gl-dropdown-item>Fourth item</gl-dropdown-item>`,
|
|
278
281
|
mounted() {
|
|
279
282
|
clickDropdown(this);
|
|
280
283
|
},
|
|
@@ -151,7 +151,9 @@ export default {
|
|
|
151
151
|
return !this.split;
|
|
152
152
|
},
|
|
153
153
|
isIconOnly() {
|
|
154
|
-
return Boolean(
|
|
154
|
+
return Boolean(
|
|
155
|
+
this.icon && (!this.text?.length || this.textSrOnly) && !this.hasSlotContents('button-text')
|
|
156
|
+
);
|
|
155
157
|
},
|
|
156
158
|
isIconWithText() {
|
|
157
159
|
return Boolean(this.icon && this.text?.length && !this.textSrOnly);
|
|
@@ -282,8 +284,8 @@ export default {
|
|
|
282
284
|
</div>
|
|
283
285
|
<template #button-content>
|
|
284
286
|
<slot name="button-content">
|
|
285
|
-
<gl-loading-icon v-if="loading" class="gl-mr-2" />
|
|
286
|
-
<gl-icon v-if="icon" class="dropdown-icon" :name="icon" />
|
|
287
|
+
<gl-loading-icon v-if="loading" :class="{ 'gl-mr-2': !isIconOnly }" />
|
|
288
|
+
<gl-icon v-if="icon && !(isIconOnly && loading)" class="dropdown-icon" :name="icon" />
|
|
287
289
|
<span class="gl-new-dropdown-button-text" :class="{ 'gl-sr-only': textSrOnly }">
|
|
288
290
|
<slot name="button-text">{{ buttonText }}</slot>
|
|
289
291
|
</span>
|