import { nextTick } from 'vue' import { mount } from '@vue/test-utils' import { describe, expect, it, test } from 'vitest' import { ElFormItem } from '@element-plus/components/form' import Radio from '../src/radio.vue' import RadioGroup from '../src/radio-group.vue' import RadioButton from '../src/radio-button.vue' const _mount = (template: string, data, otherObj?) => mount({ components: { 'el-radio': Radio, 'el-radio-group': RadioGroup, 'el-radio-button': RadioButton, 'el-form-item': ElFormItem, }, template, data, ...otherObj, }) describe('Radio', () => { test('create', async () => { const wrapper = _mount( ` `, () => ({ radio: '' }) ) expect(wrapper.classes()).toContain('el-radio') await wrapper.trigger('click') expect(wrapper.classes()).toContain('is-checked') }) test('disabled', async () => { const wrapper = _mount( ` `, () => ({ radio: '' }) ) await wrapper.trigger('click') const vm = wrapper.vm as any expect(vm.radio).toBe('') expect(wrapper.classes()).toContain('is-disabled') }) test('border', () => { const wrapper = _mount( ` `, () => ({ radio: '' }) ) expect(wrapper.classes()).toContain('is-bordered') }) test('change event', async () => { const wrapper = _mount( ` `, () => ({ radio: '', changeData: '', }), { methods: { handleChange(val) { this.changeData = val }, }, } ) const vm = wrapper.vm as any await wrapper.trigger('click') await nextTick() expect(vm.changeData).toEqual('3') }) test('change event only triggers on user input', async () => { const wrapper = _mount( ` `, () => ({ radio: '', changeData: '', }), { methods: { handleChange(val) { this.changeData = val }, }, } ) const vm = wrapper.vm as any vm.radio = '3' await nextTick() expect(vm.changeData).toEqual('') expect(vm.radio).toEqual('3') }) }) describe('Radio group', () => { it('create', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) const radio1 = wrapper.findComponent({ ref: 'radio1' }) expect(radio1.classes()).toContain('is-checked') const radio2 = wrapper.findComponent({ ref: 'radio2' }) await radio2.trigger('click') expect(radio2.classes()).toContain('is-checked') const vm = wrapper.vm as any expect(vm.radio).toEqual(6) }) it('id auto derive', async () => { const wrapper1 = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) const wrapper2 = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) const id1 = wrapper1 .findComponent({ name: 'ElRadio' }) .find('input') .attributes('name') const id2 = wrapper2 .findComponent({ name: 'ElRadio' }) .find('input') .attributes('name') expect(id1).not.toEqual(id2) }) it('disabled', async () => { const wrapper = _mount( ` 3 6 7 `, () => ({ radio: 3, }) ) expect(wrapper.find('label.is-disabled').exists()).toBe(true) const radio1 = wrapper.findComponent({ ref: 'radio1' }) expect(radio1.classes()).toContain('is-checked') const radio2 = wrapper.findComponent({ ref: 'radio2' }) await radio2.trigger('click') const vm = wrapper.vm as any expect(vm.radio).toEqual(3) expect(radio1.classes()).toContain('is-checked') }) it('change event', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, data: 0, }), { methods: { onChange(val) { this.data = val }, }, } ) const radio2 = wrapper.findComponent({ ref: 'radio2' }) await radio2.trigger('click') await nextTick() const vm = wrapper.vm as any expect(vm.data).toEqual(6) }) it('change event only triggers on user input', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, data: 0, }), { methods: { onChange(val) { this.data = val }, }, } ) const vm = wrapper.vm as any vm.radio = 6 await nextTick() expect(vm.data).toEqual(0) }) it('disabled when children is radio button', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) const radio1 = wrapper.findComponent({ ref: 'radio1' }) const radio2 = wrapper.findComponent({ ref: 'radio2' }) expect(radio1.classes()).toContain('is-active') expect(wrapper.findAll('.is-disabled').length).toBe(3) await radio2.trigger('click') const vm = wrapper.vm as any expect(vm.radio).toEqual(3) expect(radio1.classes()).toContain('is-active') }) }) describe('Radio Button', () => { it('create', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) const radio1 = wrapper.findComponent({ ref: 'radio1' }) expect(radio1.classes()).toContain('is-active') const radio2 = wrapper.findComponent({ ref: 'radio2' }) await radio2.trigger('click') expect(radio2.classes()).toContain('is-active') const vm = wrapper.vm as any expect(vm.radio).toEqual(6) }) it('custom color', () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) const radio1 = wrapper.findComponent({ ref: 'radio1' }) expect(radio1.find('span').attributes('style')).toContain( 'background-color: rgb(0, 0, 0); border-color: #000; box-shadow: -1px 0 0 0 #000; color: rgb(255, 255, 0);' ) }) it('change event', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ data: 0, radio: 3, }), { methods: { onChange(val) { this.data = val }, }, } ) const radio2 = wrapper.findComponent({ ref: 'radio2' }) await radio2.trigger('click') const vm = wrapper.vm as any expect(vm.radio).toEqual(6) }) it('change event only triggers on user input', async () => { const wrapper = _mount( ` 3 6 9 `, () => ({ data: 0, radio: 3, }), { methods: { onChange(val) { this.data = val }, }, } ) const vm = wrapper.vm as any vm.radio = 6 await nextTick() expect(vm.data).toEqual(0) }) it('size', () => { const wrapper = _mount( ` 3 6 9 `, () => ({ radio: 3, }) ) expect(wrapper.findAll('.el-radio-button--large').length).toBe(3) }) describe('form item accessibility integration', () => { test('single radio group in form item', async () => { const wrapper = _mount( ` `, () => ({}) ) await nextTick() const formItem = await wrapper.findComponent({ ref: 'item' }) const radioGroup = await wrapper.findComponent({ ref: 'radioGroup', }) const formItemLabel = formItem.find('.el-form-item__label') expect(formItem.attributes().role).toBeFalsy() expect(radioGroup.attributes().role).toBe('radiogroup') expect(formItemLabel.attributes().for).toBe(radioGroup.attributes().id) expect(formItemLabel.attributes().id).toBe( radioGroup.attributes()['aria-labelledby'] ) }) test('single radio group in form item, override label', async () => { const wrapper = _mount( ` `, () => ({}) ) await nextTick() const formItem = await wrapper.findComponent({ ref: 'item' }) const radioGroup = await wrapper.findComponent({ ref: 'radioGroup', }) const formItemLabel = formItem.find('.el-form-item__label') expect(formItemLabel.attributes().for).toBe(radioGroup.attributes().id) expect(radioGroup.attributes().role).toBe('radiogroup') expect(radioGroup.attributes()['aria-label']).toBe('Foo') expect(radioGroup.attributes()['aria-labelledby']).toBeFalsy() }) test('multiple radio groups in form item', async () => { const wrapper = _mount( ` `, () => ({}) ) await nextTick() const formItem = await wrapper.findComponent({ ref: 'item' }) const radioGroup1 = await wrapper.findComponent({ ref: 'radioGroup1', }) const radioGroup2 = await wrapper.findComponent({ ref: 'radioGroup2', }) const formItemLabel = formItem.find('.el-form-item__label') expect(formItem.attributes().role).toBe('group') expect(formItem.attributes()['aria-labelledby']).toBe( formItemLabel.attributes().id ) expect(radioGroup1.attributes().role).toBe('radiogroup') expect(radioGroup1.attributes()['aria-label']).toBe('Foo') expect(radioGroup1.attributes()['aria-labelledby']).toBeFalsy() expect(radioGroup2.attributes().role).toBe('radiogroup') expect(radioGroup2.attributes()['aria-label']).toBe('Bar') expect(radioGroup2.attributes()['aria-labelledby']).toBeFalsy() }) }) })