← Components/Layouts

SplitPane

splitpane-1779394345462.tsx
'use client'
import { useState, useRef, useCallback } from 'react'

export default function SplitPane({ direction = 'horizontal', minSize = 100 }) {
  const [split, setSplit] = useState(50)
  const container = useRef(null)
  const dragging = useRef(false)
  const onMouseDown = () => { dragging.current = true }
  const onMouseMove = useCallback((e) => {
    if (!dragging.current || !container.current) return
    const rect = container.current.getBoundingClientRect()
    const pos = direction === 'horizontal' ? e.clientX - rect.left : e.clientY - rect.top
    const total = direction === 'horizontal' ? rect.width : rect.height
    const pct = Math.min(Math.max((pos / total) * 100, (minSize/total)*100), 100-(minSize/total)*100)
    setSplit(pct)
  }, [direction, minSize])
  const onMouseUp = () => { dragging.current = false }
  return (
    <div ref={container} onMouseMove={onMouseMove} onMouseUp={onMouseUp} onMouseLeave={onMouseUp}
      style={{ display:'flex', flexDirection:direction==='horizontal'?'row':'column', height:'300px', border:'1px solid #e2e8f0', borderRadius:'12px', overflow:'hidden', userSelect:'none' }}>
      <div style={{ [direction==='horizontal'?'width':'height']:split+'%', background:'#f8fafc', overflow:'auto', padding:'16px', transition:'none' }}>
        <div style={{ fontWeight:600, color:'#374151', marginBottom:'8px', fontSize:'13px', textTransform:'uppercase', letterSpacing:'0.05em' }}>Panel A</div>
        <div style={{ fontSize:'13px', color:'#64748b', lineHeight:1.6 }}>Drag the divider to resize panels. This panel contains your primary content area with scrollable content.</div>
      </div>
      <div onMouseDown={onMouseDown} style={{
        [direction==='horizontal'?'width':'height']:'6px',
        background:'#e2e8f0', cursor:direction==='horizontal'?'col-resize':'row-resize',
        flexShrink:0, position:'relative', display:'flex', alignItems:'center', justifyContent:'center',
      }}>
        <div style={{ [direction==='horizontal'?'width':'height']:'2px', [direction==='horizontal'?'height':'width']:'24px', background:'#94a3b8', borderRadius:'1px' }} />
      </div>
      <div style={{ flex:1, background:'#fff', overflow:'auto', padding:'16px' }}>
        <div style={{ fontWeight:600, color:'#374151', marginBottom:'8px', fontSize:'13px', textTransform:'uppercase', letterSpacing:'0.05em' }}>Panel B</div>
        <div style={{ fontSize:'13px', color:'#64748b', lineHeight:1.6 }}>Secondary content area. The split ratio is {Math.round(split)}% / {Math.round(100-split)}%.</div>
      </div>
    </div>
  )
}

Component info

CategoryLayouts
Frameworkreact
TierFREE
Views0
Copies0

About

Resizable split pane with horizontal or vertical orientation

More from Layouts

'use client'
import { useState, useRef, useCallback, useEffect } from 'react'

export default function SplitPane() {
  const [split, setSplit] = useState(50)
  const [dragging, setDragging] = useState(false)
  const [collapsed, setCollapsed] = useSta
SplitPane
Layouts
'use client'
import { useState } from 'react'

interface Block {
  id: number
  label: string
  color: string
  colSpan: number
  rowSpan: number
}

const INITIAL: Block[] = [
  { id: 1, label: 'Header', color: '#C9A84C', colSpan: 12, rowSpan: 1 },
 
GridLayout
Layouts
'use client'
import { useState } from 'react'

const ITEMS = [
  { id: 1, title: 'What is Empire UI?', content: 'Empire UI is a library of 17,500 AI-generated React components.' },
  { id: 2, title: 'How to install?', content: 'Install via npm or use
Accordion
Layouts
'use client'
import { useState } from 'react'

const INIT = [
  { id:1, label:'Design System Audit', priority:'P1' },
  { id:2, label:'API Integration', priority:'P2' },
  { id:3, label:'Performance Review', priority:'P1' },
  { id:4, label:'Mobile R
DragList
Layouts