diff --git a/docs/demo/fragment.md b/docs/demo/fragment.md
deleted file mode 100644
index de859a4..0000000
--- a/docs/demo/fragment.md
+++ /dev/null
@@ -1,8 +0,0 @@
----
-title: fragment
-nav:
-  title: Demo
-  path: /demo
----
-
-
,
+            },
+          ]}
+        />
+      ),
+    },
+    {
+      key: initLength + 2,
+      header: `This is panel header ${initLength + 2}`,
+      children: (
+        
+                  
+                  
+                
+              ),
+            },
+          ]}
+        />
+      ),
+    },
   );
 
   const tools = (
@@ -104,9 +128,8 @@ const App: React.FC = () => {
         activeKey={activeKey}
         expandIcon={expandIcon}
         openMotion={motion}
-      >
-        {panelItems}
-      
+        items={panelItems}
+      />
     >
   );
 };
diff --git a/docs/examples/fragment.tsx b/docs/examples/fragment.tsx
deleted file mode 100644
index bb38c5b..0000000
--- a/docs/examples/fragment.tsx
+++ /dev/null
@@ -1,23 +0,0 @@
-import Collapse, { Panel } from 'rc-collapse';
-import * as React from 'react';
-import { Fragment } from 'react';
-import '../../assets/index.less';
-
-const App = () => (
-  
-    content
-    content
-    
-      content
-      content
-    
-    
-      
-        content
-        content
-      
-    
-  
-);
-
-export default App;
diff --git a/docs/examples/simple.tsx b/docs/examples/simple.tsx
index 5353415..2201d43 100644
--- a/docs/examples/simple.tsx
+++ b/docs/examples/simple.tsx
@@ -1,7 +1,8 @@
 import type { CollapseProps } from 'rc-collapse';
-import Collapse, { Panel } from 'rc-collapse';
+import Collapse from 'rc-collapse';
 import * as React from 'react';
 import '../../assets/index.less';
+import type { ItemType } from '../../src/interface';
 import motion from './_util/motionUtil';
 
 const initLength = 3;
@@ -50,38 +51,60 @@ const App: React.FC = () => {
 
   const time = random();
 
-  const panelItems = Array.from({ length: initLength }, (_, i) => {
+  const panelItems = Array.from({ length: initLength }, (_, i) => {
     const key = i + 1;
-    return (
-      
-        {text.repeat(time)}
-      
-    );
+    return {
+      key,
+      header: `This is panel header ${key}`,
+      children: {text.repeat(time)}
,
+    };
   }).concat(
-    
-      
-        
-      
-    ,
-    
-      
-        
-          
-        
-      
-    ,
-    Extra Node}
-    >
-      Panel with extra
-    ,
+    {
+      key: initLength + 1,
+      header: `This is panel header ${initLength + 1}`,
+      children: (
+        {text},
+            },
+          ]}
+        />
+      ),
+    },
+    {
+      key: initLength + 2,
+      header: `This is panel header ${initLength + 2}`,
+      children: (
+        
+                  
+                  
+                
+              ),
+            },
+          ]}
+        />
+      ),
+    },
+    {
+      key: initLength + 3,
+      header: `This is panel header ${initLength + 3}`,
+      extra: Extra Node,
+      children: Panel with extra
,
+    },
   );
 
   const handleCollapsibleChange = (e: React.ChangeEvent) => {
@@ -129,9 +152,8 @@ const App: React.FC = () => {
         expandIcon={expandIcon}
         openMotion={motion}
         collapsible={collapsible}
-      >
-        {panelItems}
-      
+        items={panelItems}
+      />
     >
   );
 };
diff --git a/src/Collapse.tsx b/src/Collapse.tsx
index 36267d2..52519ef 100644
--- a/src/Collapse.tsx
+++ b/src/Collapse.tsx
@@ -1,6 +1,5 @@
 import classNames from 'classnames';
 import useMergedState from 'rc-util/lib/hooks/useMergedState';
-import warning from 'rc-util/lib/warning';
 import React from 'react';
 import useItems from './hooks/useItems';
 import type { CollapseProps } from './interface';
@@ -23,7 +22,6 @@ const Collapse = React.forwardRef((props, ref) =>
     style,
     accordion,
     className,
-    children,
     collapsible,
     openMotion,
     expandIcon,
@@ -58,12 +56,7 @@ const Collapse = React.forwardRef((props, ref) =>
     });
 
   // ======================== Children ========================
-  warning(
-    !children,
-    '`children` will be removed in next major version. Please use `items` instead.',
-  );
-
-  const mergedChildren = useItems(items, children, {
+  const mergedChildren = useItems(items, {
     prefixCls,
     accordion,
     openMotion,
diff --git a/src/hooks/useItems.tsx b/src/hooks/useItems.tsx
index 2bc5db7..cc39737 100644
--- a/src/hooks/useItems.tsx
+++ b/src/hooks/useItems.tsx
@@ -1,4 +1,3 @@
-import toArray from 'rc-util/lib/Children/toArray';
 import React from 'react';
 import type { CollapsePanelProps, CollapseProps, ItemType } from '../interface';
 import CollapsePanel from '../Panel';
@@ -31,8 +30,6 @@ const convertItemsToNodes = (items: ItemType[], props: Props) => {
       ...restProps
     } = item;
 
-    // You may be puzzled why you want to convert them all into strings, me too.
-    // Maybe: https://github.com/react-component/collapse/blob/aac303a8b6ff30e35060b4f8fecde6f4556fcbe2/src/Collapse.tsx#L15
     const key = String(rawKey ?? index);
     const mergeCollapsible = rawCollapsible ?? collapsible;
     const mergeDestroyInactivePanel = rawDestroyInactivePanel ?? destroyInactivePanel;
@@ -71,92 +68,12 @@ const convertItemsToNodes = (items: ItemType[], props: Props) => {
   });
 };
 
-/**
- * @deprecated The next major version will be removed
- */
-const getNewChild = (
-  child: React.ReactElement,
-  index: number,
-  props: Props,
-) => {
-  if (!child) return null;
-
-  const {
-    prefixCls,
-    accordion,
-    collapsible,
-    destroyInactivePanel,
-    onItemClick,
-    activeKey,
-    openMotion,
-    expandIcon,
-  } = props;
-
-  const key = child.key || String(index);
-
-  const {
-    header,
-    headerClass,
-    destroyInactivePanel: childDestroyInactivePanel,
-    collapsible: childCollapsible,
-    onItemClick: childOnItemClick,
-  } = child.props;
-
-  let isActive = false;
-  if (accordion) {
-    isActive = activeKey[0] === key;
-  } else {
-    isActive = activeKey.indexOf(key) > -1;
-  }
-
-  const mergeCollapsible = childCollapsible ?? collapsible;
-
-  const handleItemClick = (value: React.Key) => {
-    if (mergeCollapsible === 'disabled') return;
-    onItemClick(value);
-    childOnItemClick?.(value);
-  };
-
-  const childProps = {
-    key,
-    panelKey: key,
-    header,
-    headerClass,
-    isActive,
-    prefixCls,
-    destroyInactivePanel: childDestroyInactivePanel ?? destroyInactivePanel,
-    openMotion,
-    accordion,
-    children: child.props.children,
-    onItemClick: handleItemClick,
-    expandIcon,
-    collapsible: mergeCollapsible,
-  };
-
-  // https://github.com/ant-design/ant-design/issues/20479
-  if (typeof child.type === 'string') {
-    return child;
-  }
-
-  Object.keys(childProps).forEach((propName) => {
-    if (typeof childProps[propName] === 'undefined') {
-      delete childProps[propName];
-    }
-  });
-
-  return React.cloneElement(child, childProps);
-};
-
-function useItems(
-  items?: ItemType[],
-  rawChildren?: React.ReactNode,
-  props?: Props,
-): React.ReactElement[] {
+function useItems(items?: ItemType[], props?: Props) {
   if (Array.isArray(items)) {
     return convertItemsToNodes(items, props);
   }
 
-  return toArray(rawChildren).map((child, index) => getNewChild(child, index, props));
+  return null;
 }
 
 export default useItems;
diff --git a/src/index.tsx b/src/index.tsx
index 8e963c6..87e21e7 100644
--- a/src/index.tsx
+++ b/src/index.tsx
@@ -1,10 +1,2 @@
-import Collapse from './Collapse';
-
+export { default } from './Collapse';
 export type { CollapsePanelProps, CollapseProps } from './interface';
-
-export default Collapse;
-
-/**
- * @deprecated use `items` instead, will be removed in `v4.0.0`
- */
-export const { Panel } = Collapse;
diff --git a/tests/index.spec.tsx b/tests/index.spec.tsx
index 533df08..cd2a509 100644
--- a/tests/index.spec.tsx
+++ b/tests/index.spec.tsx
@@ -1,8 +1,8 @@
 import type { RenderResult } from '@testing-library/react';
 import { fireEvent, render } from '@testing-library/react';
 import KeyCode from 'rc-util/lib/KeyCode';
-import React, { Fragment } from 'react';
-import Collapse, { Panel } from '../src/index';
+import React from 'react';
+import Collapse from '../src/index';
 import type { CollapseProps, ItemType } from '../src/interface';
 
 describe('collapse', () => {
@@ -24,6 +24,27 @@ describe('collapse', () => {
     }
   }
 
+  const items: ItemType[] = [
+    {
+      key: '1',
+      label: 'collapse 1',
+      collapsible: 'disabled',
+      children: 'first',
+    },
+    {
+      key: '2',
+      label: 'collapse 2',
+      extra: ExtraSpan,
+      children: 'second',
+    },
+    {
+      key: '3',
+      label: 'collapse 3',
+      className: 'important',
+      children: 'third',
+    },
+  ];
+
   function runNormalTest(element: any) {
     let collapse: RenderResult;
 
@@ -115,21 +136,7 @@ describe('collapse', () => {
   describe('collapse', () => {
     const expandIcon = () => test{'>'};
 
-    const element = (
-      
-        
-          first
-        
-        ExtraSpan}>
-          second
-        
-        
-          third
-        
-      
-    );
-
-    runNormalTest(element);
+    runNormalTest();
 
     it('controlled', () => {
       const onChangeSpy = jest.fn();
@@ -143,17 +150,27 @@ describe('collapse', () => {
         };
 
         return (
-          
-            
-              first
-            
-            
-              second
-            
-            
-              third
-            
-          
+          
         );
       };
 
@@ -170,31 +187,32 @@ describe('collapse', () => {
   });
 
   describe('it should support number key', () => {
-    const expandIcon = () => test{'>'};
-    const element = (
-      
-        
-          first
-        
-        ExtraSpan}>
-          second
-        
-        
-          third
-        
-      
+    runNormalTest(
+       test{'>'}}
+        items={items.map((item) => ({
+          ...item,
+          key: Number(item.key),
+        }))}
+      />,
     );
-
-    runNormalTest(element);
   });
 
   it('shoule support extra whit number 0', () => {
     const { container } = render(
-      
-        
-          zero
-        
-      ,
+      ,
     );
 
     const extraNodes = container.querySelectorAll('.rc-collapse-extra');
@@ -204,17 +222,14 @@ describe('collapse', () => {
 
   it('should support activeKey number 0', () => {
     const { container } = render(
-      
-        
-          zero
-        
-        
-          first
-        
-        
-          second
-        
-      ,
+       ({
+          ...item,
+          key: index,
+        }))}
+      />,
     );
 
     // activeKey number 0, should open one item
@@ -223,17 +238,7 @@ describe('collapse', () => {
 
   it('click should toggle panel state', () => {
     const { container } = render(
-      
-        
-          first
-        
-        
-          second
-        
-        
-          third
-        
-      ,
+      ,
     );
 
     const header = container.querySelectorAll('.rc-collapse-header')?.[1];
@@ -313,59 +318,89 @@ describe('collapse', () => {
 
   describe('prop: accordion', () => {
     runAccordionTest(
-      
-        
-          first
-        
-        
-          second
-        
-        
-          third
-        
-      ,
+      ,
     );
   });
 
   describe('forceRender', () => {
     it('when forceRender is not supplied it should lazy render the panel content', () => {
       const { container } = render(
-        
-          
-            first
-          
-          
-            second
-          
-        ,
+        ,
       );
       expect(container.querySelectorAll('.rc-collapse-content')).toHaveLength(0);
     });
 
     it('when forceRender is FALSE it should lazy render the panel content', () => {
       const { container } = render(
-        
-          
-            first
-          
-          
-            second
-          
-        ,
+        ,
       );
       expect(container.querySelectorAll('.rc-collapse-content')).toHaveLength(0);
     });
 
     it('when forceRender is TRUE then it should render all the panel content to the DOM', () => {
       const { container } = render(
-        
-          
-            first
-          
-          
-            second
-          
-        ,
+        ,
       );
 
       jest.runAllTimers();
@@ -388,17 +423,26 @@ describe('collapse', () => {
     };
 
     const { container } = render(
-      
-        
-          first
-        
-        
-          second
-        
-        
-          second
-        
-      ,
+      ,
     );
 
     fireEvent.keyPress(container.querySelectorAll('.rc-collapse-header')?.[2], myKeyEvent);
@@ -423,46 +467,59 @@ describe('collapse', () => {
     );
   });
 
-  describe('wrapped in Fragment', () => {
-    const expandIcon = () => test{'>'};
-    const element = (
-      
-        
-          
-            first
-          
-          ExtraSpan}>
-            second
-          
-          
-            
-              third
-            
-          
-        
-      
-    );
-
-    runNormalTest(element);
-  });
+  // TODO: 移除 Panel 后需要在 Ant Design 里面测试,待 Ant Design 稳定后再移除 assignee: @wxh16144
+  // describe('wrapped in Fragment', () => {
+  //   const expandIcon = () => test{'>'};
+  //   const element = (
+  //     
+  //       
+  //         
+  //           first
+  //         
+  //         ExtraSpan}>
+  //           second
+  //         
+  //         
+  //           
+  //             third
+  //           
+  //         
+  //       
+  //     
+  //   );
+
+  //   runNormalTest(element);
+  // });
 
   it('should support return null icon', () => {
     const { container } = render(
-       null}>
-        
-          first
-        
-      ,
+       null}
+        items={[
+          {
+            key: '1',
+            label: 'title',
+            children: 'first',
+          },
+        ]}
+      />,
     );
     expect(container.querySelector('.rc-collapse-header')?.childNodes).toHaveLength(1);
   });
 
-  it('should support custom child', () => {
+  // TODO: 需要在 Ant Design 里面测试,待 Ant Design 稳定后再移除 assignee: @wxh16144
+  // 按理说我们不允许用户这样用,但是为了兼容性,我们还是保留这个测试
+  it.skip('should support custom child', () => {
     const { container } = render(
-      
-        
-          first
-        
+      
         custom-child
       ,
     );
@@ -472,44 +529,49 @@ describe('collapse', () => {
   // https://github.com/ant-design/ant-design/issues/36327
   // https://github.com/ant-design/ant-design/issues/6179
   // https://github.com/react-component/collapse/issues/73#issuecomment-323626120
-  it('should support custom component', () => {
-    const PanelElement = (props) => (
-      
-        test
-      
-    );
-    const { container } = render(
-      
-        
-        
-          second
-        
-      ,
-    );
-
-    expect(container.querySelectorAll('.rc-collapse-content-active')).toHaveLength(1);
-    expect(container.querySelector('.rc-collapse-content')).toHaveClass(
-      'rc-collapse-content-active',
-    );
-    expect(container.querySelector('.rc-collapse-header')?.textContent).toBe('collapse 1');
-    expect(container.querySelector('.rc-collapse-header')?.querySelectorAll('.arrow')).toHaveLength(
-      1,
-    );
-    fireEvent.click(container.querySelector('.rc-collapse-header')!);
-    expect(container.querySelectorAll('.rc-collapse-content-active')).toHaveLength(0);
-    expect(container.querySelector('.rc-collapse-content')).toHaveClass(
-      'rc-collapse-content-inactive',
-    );
-  });
+  // TODO: 需要在 Ant Design 里面测试,待 Ant Design 稳定后再移除 assignee: @wxh16144
+  // it('should support custom component', () => {
+  //   const PanelElement = (props) => (
+  //     
+  //       test
+  //     
+  //   );
+  //   const { container } = render(
+  //     
+  //       
+  //       
+  //         second
+  //       
+  //     ,
+  //   );
+
+  //   expect(container.querySelectorAll('.rc-collapse-content-active')).toHaveLength(1);
+  //   expect(container.querySelector('.rc-collapse-content')).toHaveClass(
+  //     'rc-collapse-content-active',
+  //   );
+  //   expect(container.querySelector('.rc-collapse-header')?.textContent).toBe('collapse 1');
+  //   expect(container.querySelector('.rc-collapse-header')?.querySelectorAll('.arrow')).toHaveLength(
+  //     1,
+  //   );
+  //   fireEvent.click(container.querySelector('.rc-collapse-header')!);
+  //   expect(container.querySelectorAll('.rc-collapse-content-active')).toHaveLength(0);
+  //   expect(container.querySelector('.rc-collapse-content')).toHaveClass(
+  //     'rc-collapse-content-inactive',
+  //   );
+  // });
 
   describe('prop: collapsible', () => {
     it('default', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
       expect(container.querySelector('.rc-collapse-header-text')).toBeTruthy();
       fireEvent.click(container.querySelector('.rc-collapse-header')!);
@@ -517,11 +579,16 @@ describe('collapse', () => {
     });
     it('should work when value is header', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
       expect(container.querySelector('.rc-collapse-header-text')).toBeTruthy();
       fireEvent.click(container.querySelector('.rc-collapse-header')!);
@@ -531,11 +598,16 @@ describe('collapse', () => {
     });
     it('should work when value is icon', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
       expect(container.querySelector('.rc-collapse-expand-icon')).toBeTruthy();
       fireEvent.click(container.querySelector('.rc-collapse-header')!);
@@ -546,11 +618,16 @@ describe('collapse', () => {
 
     it('should disabled when value is disabled', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
       expect(container.querySelector('.rc-collapse-header-text')).toBeTruthy();
       expect(container.querySelectorAll('.rc-collapse-item-disabled')).toHaveLength(1);
@@ -560,11 +637,17 @@ describe('collapse', () => {
 
     it('the value of panel should be read first', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
       expect(container.querySelector('.rc-collapse-header-text')).toBeTruthy();
 
@@ -576,11 +659,16 @@ describe('collapse', () => {
 
     it('icon trigger when collapsible equal header', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
 
       fireEvent.click(container.querySelector('.rc-collapse-header .arrow')!);
@@ -589,11 +677,16 @@ describe('collapse', () => {
 
     it('header not trigger when collapsible equal icon', () => {
       const { container } = render(
-        
-          
-            first
-          
-        ,
+        ,
       );
 
       fireEvent.click(container.querySelector('.rc-collapse-header-text')!);
@@ -603,11 +696,16 @@ describe('collapse', () => {
 
   it('!showArrow', () => {
     const { container } = render(
-      
-        
-          first
-        
-      ,
+      ,
     );
 
     expect(container.querySelectorAll('.rc-collapse-expand-icon')).toHaveLength(0);
@@ -616,46 +714,38 @@ describe('collapse', () => {
   it('Panel container dom can set event handler', () => {
     const clickHandler = jest.fn();
     const { container } = render(
-      
-        
-          Click this
-        
-      ,
+      Click this,
+          },
+        ]}
+      />,
     );
 
     fireEvent.click(container.querySelector('.target')!);
     expect(clickHandler).toHaveBeenCalled();
   });
 
-  it('falsy Panel', () => {
-    const { container } = render(
-      
-        {null}
-        
-          Panel 1 content
-        
-        {0}
-        
-          Panel 2 content
-        
-        {undefined}
-        {false}
-        {true}
-      ,
-    );
-
-    expect(container.querySelectorAll('.rc-collapse-item')).toHaveLength(2);
-  });
-
   it('ref should work', () => {
     const ref = React.createRef();
     const panelRef = React.createRef();
     const { container } = render(
-      
-        
-          first
-        
-      ,
+      ,
     );
     expect(ref.current).toBe(container.firstChild);
     expect(panelRef.current).toBe(container.querySelector('.rc-collapse-item'));
@@ -665,11 +755,16 @@ describe('collapse', () => {
   it('onItemClick should work', () => {
     const onItemClick = jest.fn();
     const { container } = render(
-      
-        
-          first
-        
-      ,
+      ,
     );
     fireEvent.click(container.querySelector('.rc-collapse-header')!);
     expect(onItemClick).toHaveBeenCalled();
@@ -678,11 +773,17 @@ describe('collapse', () => {
   it('onItemClick should not work when collapsible is disabled', () => {
     const onItemClick = jest.fn();
     const { container } = render(
-      
-        
-          first
-        
-      ,
+      ,
     );
     fireEvent.click(container.querySelector('.rc-collapse-header')!);
     expect(onItemClick).not.toHaveBeenCalled();
@@ -690,65 +791,24 @@ describe('collapse', () => {
 
   it('panel style should work', () => {
     const { container } = render(
-      
-        
-          first
-        
-      ,
-    );
-    expect(container.querySelector('.rc-collapse-item').style.color).toBe('red');
-  });
-
-  describe('props items', () => {
-    const items: ItemType[] = [
-      {
-        key: '1',
-        label: 'collapse 1',
-        children: 'first',
-        collapsible: 'disabled',
-      },
-      {
-        key: '2',
-        label: 'collapse 2',
-        children: 'second',
-        extra: ExtraSpan,
-      },
-      {
-        key: '3',
-        label: 'collapse 3',
-        className: 'important',
-        children: 'third',
-      },
-    ];
-
-    runNormalTest(
-       test{'>'}} items={items} />,
-    );
-
-    runAccordionTest(
       ,
     );
+    expect(window.getComputedStyle(container.querySelector('.rc-collapse-item'))).toHaveProperty(
+      'color',
+      'red',
+    );
+  });
 
+  describe('props items', () => {
     it('should work with onItemClick', () => {
       const onItemClick = jest.fn();
       const { container } = render(