mirror of https://github.com/sgoudham/carbon.git
add 'width' option for Carbon container (#949)
* feat: add 'width' option for Carbon container * feat: draggable width adjustment * chore: auto disable widthAdjustment when edge starts dragging * remove label width default; tweak settings style * use only right width handler * use react effects, add a11y role and props * clean up code * use clamp fn * move max and min widths out of state * give WidthHandler a display name * tweak variable names Co-authored-by: Mike Fix <mrfix84@gmail.com> Co-authored-by: repo-ranger[bot] <39074581+repo-ranger[bot]@users.noreply.github.com>main
parent
249f94851d
commit
41722923d5
@ -0,0 +1,73 @@
|
|||||||
|
import React from 'react'
|
||||||
|
import { DEFAULT_WIDTHS, COLORS } from '../lib/constants'
|
||||||
|
|
||||||
|
const { minWidth, maxWidth } = DEFAULT_WIDTHS
|
||||||
|
|
||||||
|
function clamp(value, min, max) {
|
||||||
|
if (value < min) {
|
||||||
|
return min
|
||||||
|
}
|
||||||
|
if (value > max) {
|
||||||
|
return max
|
||||||
|
}
|
||||||
|
return value
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function WidthHandler(props) {
|
||||||
|
const { onChange, innerRef, paddingHorizontal } = props
|
||||||
|
|
||||||
|
const startX = React.useRef(null)
|
||||||
|
const startWidth = React.useRef(null)
|
||||||
|
|
||||||
|
React.useEffect(() => {
|
||||||
|
function handleMouseMove(e) {
|
||||||
|
if (!startX.current) return
|
||||||
|
|
||||||
|
const delta = e.pageX - startX.current // leftOrRight === 'left' ? startX - e.pageX : (startX - e.pageX) * -1
|
||||||
|
const calculated = startWidth.current + delta * window.devicePixelRatio
|
||||||
|
const newWidth = clamp(calculated, minWidth, maxWidth)
|
||||||
|
|
||||||
|
onChange(newWidth)
|
||||||
|
}
|
||||||
|
|
||||||
|
window.addEventListener('mousemove', handleMouseMove)
|
||||||
|
return () => window.removeEventListener('mousemove', handleMouseMove)
|
||||||
|
}, [innerRef, onChange])
|
||||||
|
|
||||||
|
return (
|
||||||
|
// eslint-disable-next-line
|
||||||
|
<div
|
||||||
|
className="handler"
|
||||||
|
onMouseDown={e => {
|
||||||
|
startX.current = e.pageX
|
||||||
|
startWidth.current = innerRef.current.clientWidth
|
||||||
|
}}
|
||||||
|
onMouseUp={() => {
|
||||||
|
startX.current = null
|
||||||
|
}}
|
||||||
|
role="separator"
|
||||||
|
aria-orientation="vertical"
|
||||||
|
aria-valuemin={minWidth}
|
||||||
|
aria-valuemax={maxWidth}
|
||||||
|
>
|
||||||
|
<style jsx>
|
||||||
|
{`
|
||||||
|
.handler {
|
||||||
|
z-index: 2;
|
||||||
|
position: absolute;
|
||||||
|
background-color: ${COLORS.BLUE};
|
||||||
|
top: ${paddingHorizontal};
|
||||||
|
bottom: ${paddingHorizontal};
|
||||||
|
right: ${paddingHorizontal};
|
||||||
|
width: 8px;
|
||||||
|
cursor: ew-resize;
|
||||||
|
opacity: 0;
|
||||||
|
}
|
||||||
|
.handler:hover {
|
||||||
|
opacity: 0.4;
|
||||||
|
}
|
||||||
|
`}
|
||||||
|
</style>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
Loading…
Reference in New Issue