From edb7a22b7f0d91850a06b0518c63b929d404aa6f Mon Sep 17 00:00:00 2001 From: Wanpan Date: Fri, 23 Aug 2024 14:22:38 +0800 Subject: [PATCH] feat: support classNames and styles (#350) * feat: support classNames and styles * feat: content to body * feat: Modifying the DOM structure * feat: add default value * fix: Animation does not meet expectations * fix: update --- README.md | 14 +++++++++++++- src/Panel.tsx | 19 ++++++++++++++----- src/PanelContent.tsx | 19 +++++++++++++++++-- src/interface.ts | 2 ++ tests/index.spec.tsx | 32 +++++++++++++++++++++++++++----- tsconfig.json | 9 ++++++++- 6 files changed, 81 insertions(+), 14 deletions(-) diff --git a/README.md b/README.md index e126af6..1a24599 100644 --- a/README.md +++ b/README.md @@ -130,7 +130,7 @@ If `accordion` is true, only one panel can be open. Opening another panel will c name - type + type default description @@ -160,12 +160,24 @@ If `accordion` is true, only one panel can be open. Opening another panel will c custom className to apply + + classNames + { header?: string, body?: string } + + Semantic structure className + style object custom style + + styles + { header?: React.CSSProperties, body?: React.CSSProperties } + + Semantic structure styles + openMotion object diff --git a/src/Panel.tsx b/src/Panel.tsx index 24860d1..5fbca54 100644 --- a/src/Panel.tsx +++ b/src/Panel.tsx @@ -13,6 +13,8 @@ const CollapsePanel = React.forwardRef((prop onItemClick, forceRender, className, + classNames: customizeClassNames = {}, + styles = {}, prefixCls, collapsible, accordion, @@ -64,11 +66,15 @@ const CollapsePanel = React.forwardRef((prop className, ); - const headerClassName = classNames(headerClass, { - [`${prefixCls}-header`]: true, - [`${prefixCls}-header-collapsible-only`]: collapsibleHeader, - [`${prefixCls}-icon-collapsible-only`]: collapsibleIcon, - }); + const headerClassName = classNames( + headerClass, + { + [`${prefixCls}-header`]: true, + [`${prefixCls}-header-collapsible-only`]: collapsibleHeader, + [`${prefixCls}-icon-collapsible-only`]: collapsibleIcon, + }, + customizeClassNames.header, + ); // ======================== HeaderProps ======================== const headerProps: React.HTMLAttributes = { @@ -76,6 +82,7 @@ const CollapsePanel = React.forwardRef((prop 'aria-expanded': isActive, 'aria-disabled': disabled, onKeyDown: handleKeyDown, + style: styles.header, }; if (!collapsibleHeader && !collapsibleIcon) { @@ -110,7 +117,9 @@ const CollapsePanel = React.forwardRef((prop ref={motionRef} prefixCls={prefixCls} className={motionClassName} + classNames={customizeClassNames} style={motionStyle} + styles={styles} isActive={isActive} forceRender={forceRender} role={accordion ? 'tabpanel' : void 0} diff --git a/src/PanelContent.tsx b/src/PanelContent.tsx index ba6d36e..37bb031 100644 --- a/src/PanelContent.tsx +++ b/src/PanelContent.tsx @@ -6,7 +6,17 @@ const PanelContent = React.forwardRef< HTMLDivElement, CollapsePanelProps & { children: React.ReactNode } >((props, ref) => { - const { prefixCls, forceRender, className, style, children, isActive, role } = props; + const { + prefixCls, + forceRender, + className, + style, + children, + isActive, + role, + classNames: customizeClassNames, + styles, + } = props; const [rendered, setRendered] = React.useState(isActive || forceRender); @@ -34,7 +44,12 @@ const PanelContent = React.forwardRef< style={style} role={role} > -
{children}
+
+ {children} +
); }); diff --git a/src/interface.ts b/src/interface.ts index 7a36bed..57e9d90 100644 --- a/src/interface.ts +++ b/src/interface.ts @@ -46,7 +46,9 @@ export interface CollapsePanelProps extends React.DOMAttributes headerClass?: string; showArrow?: boolean; className?: string; + classNames?: { header?: string; body?: string }; style?: object; + styles?: { header?: React.CSSProperties; body?: React.CSSProperties }; isActive?: boolean; openMotion?: CSSMotionProps; destroyInactivePanel?: boolean; diff --git a/tests/index.spec.tsx b/tests/index.spec.tsx index 5ae23e5..c08d7ce 100644 --- a/tests/index.spec.tsx +++ b/tests/index.spec.tsx @@ -201,7 +201,7 @@ describe('collapse', () => { const { container } = render(element); const header = container.querySelector('.rc-collapse-header'); - expect(header.classList.contains('custom-class')).toBeTruthy(); + expect(header?.classList.contains('custom-class')).toBeTruthy(); }); }); @@ -713,7 +713,7 @@ describe('collapse', () => { , ); - expect(container.querySelector('.rc-collapse-item').style.color).toBe('red'); + expect(container.querySelector('.rc-collapse-item')).toHaveStyle({ color: 'red' }); }); describe('props items', () => { @@ -778,7 +778,7 @@ describe('collapse', () => { ]} />, ); - fireEvent.click(container.querySelector('.rc-collapse-header')); + fireEvent.click(container.querySelector('.rc-collapse-header')!); expect(onItemClick).toHaveBeenCalled(); expect(onItemClick).lastCalledWith('0'); }); @@ -800,11 +800,11 @@ describe('collapse', () => { />, ); - fireEvent.click(container.querySelector('.rc-collapse-header')); + fireEvent.click(container.querySelector('.rc-collapse-header')!); expect(onItemClick).not.toHaveBeenCalled(); fireEvent.click( - container.querySelector('.rc-collapse-item:nth-child(2) .rc-collapse-expand-icon'), + container.querySelector('.rc-collapse-item:nth-child(2) .rc-collapse-expand-icon')!, ); expect(onItemClick).toHaveBeenCalled(); expect(onChangeFn).toBeCalledTimes(1); @@ -859,5 +859,27 @@ describe('collapse', () => { expect(container.querySelector('.rc-collapse')?.getAttribute('data-testid')).toBe('1234'); expect(container.querySelector('.rc-collapse')?.getAttribute('aria-label')).toBe('test'); }); + + it('should support styles and classNames', () => { + const { container } = render( + , + ); + + expect(container.querySelector('.rc-collapse-header')).toHaveClass('header-class'); + expect(container.querySelector('.rc-collapse-content-box')).toHaveClass('body-class'); + + expect(container.querySelector('.rc-collapse-header')).toHaveStyle({ color: 'red' }); + expect(container.querySelector('.rc-collapse-content-box')).toHaveStyle({ color: 'blue' }); + }); }); }); diff --git a/tsconfig.json b/tsconfig.json index bbd8b8b..bc68db4 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -13,5 +13,12 @@ "rc-collapse": ["src/index.tsx"] } }, - "include": [".dumirc.ts", "./src/**/*.ts", "./src/**/*.tsx", "./docs/**/*.tsx"] + "include": [ + ".dumirc.ts", + "./src/**/*.ts", + "./src/**/*.tsx", + "./tests/**/*.ts", + "./tests/**/*.tsx", + "./docs/**/*.tsx" + ] }