diff --git a/src/components/DxhCollapse.vue b/src/components/DxhCollapse.vue new file mode 100644 index 0000000..31f73ca --- /dev/null +++ b/src/components/DxhCollapse.vue @@ -0,0 +1,114 @@ + + + diff --git a/src/components/__tests__/DxhCollapse.spec.ts b/src/components/__tests__/DxhCollapse.spec.ts new file mode 100644 index 0000000..bcfec76 --- /dev/null +++ b/src/components/__tests__/DxhCollapse.spec.ts @@ -0,0 +1,77 @@ +import { describe, it, expect, beforeEach, afterEach } from 'vitest' +import { mount } from '@vue/test-utils' +import DxhCollapse from '@/components/DxhCollapse.vue' + +describe('DxhCollapse.vue', () => { + let wrapper: any + + beforeEach(() => { + wrapper = mount(DxhCollapse, { + props: { + items: [ + { id: 1, header: 'Header 1', content: 'Content 1' }, + { id: 2, header: 'Header 2', content: 'Content 2' } + ], + defaultActiveKey: 1, + collapsible: 'header', + expandIconPosition: 'left' + } + }) + }) + + afterEach(() => { + wrapper.unmount() + }) + + it('renders with correct initial state', () => { + const header1 = wrapper.find('[data-test="collapse-item-header-1"]') + const header2 = wrapper.find('[data-test="collapse-item-header-2"]') + const content1 = wrapper.find('[data-test="collapse-item-content-1"]') + const content2 = wrapper.find('[data-test="collapse-item-content-2"]') + + expect(header1.classes()).toContain('bg-gray-200') + expect(content1.exists()).toBe(true) + + expect(content2.exists()).toBe(false) + }) + + it('toggles active item on header click', async () => { + const header2 = wrapper.find('[data-test="collapse-item-header-2"]') + const content2 = wrapper.find('[data-test="collapse-item-content-2"]') + + await header2.trigger('click') + + expect(header2.classes()).toContain('bg-gray-200') + expect(content2.exists()).toBe(false) + + const header1 = wrapper.find('[data-test="collapse-item-header-1"]') + const content1 = wrapper.find('[data-test="collapse-item-content-1"]') + expect(header1.classes()).toContain('bg-gray-200') + expect(content1.exists()).toBe(true) + }) + + it('emits change event on item click', async () => { + const header2 = wrapper.find('[data-test="collapse-item-header-2"]') + + await header2.trigger('click') + + expect(wrapper.emitted().change).toBeTruthy() + expect(wrapper.emitted().change[0][0]).toEqual([1, 2]) + }) + + it('handles click on expand icon', async () => { + const expandIcon2 = wrapper.find('[data-test="collapse-item-expand-icon-2"]') + const content2 = wrapper.find('[data-test="collapse-item-content-2"]') + + await expandIcon2.trigger('click') + + const header2 = wrapper.find('[data-test="collapse-item-header-2"]') + expect(header2.classes()).toContain('bg-gray-200') + expect(content2.exists()).toBe(false) + + const header1 = wrapper.find('[data-test="collapse-item-header-1"]') + const content1 = wrapper.find('[data-test="collapse-item-content-1"]') + expect(header1.classes()).toContain('bg-gray-200') + expect(content1.exists()).toBe(true) + }) +}) diff --git a/src/index.ts b/src/index.ts index ee2ff8d..0babaa6 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,4 +1,5 @@ import DButton from "./components/DButton.vue" import DInput from "./components/DInput.vue" +import DxhCollapse from './components/DxhCollapse.vue' -export default {DButton, DInput} \ No newline at end of file +export default { DButton, DInput, DxhCollapse } \ No newline at end of file