Skip to content

Commit

Permalink
fix: enhance #slider on touch devices
Browse files Browse the repository at this point in the history
  • Loading branch information
tujoworker committed Nov 29, 2019
1 parent e62f55e commit 4171c3a
Show file tree
Hide file tree
Showing 3 changed files with 80 additions and 73 deletions.
148 changes: 76 additions & 72 deletions packages/dnb-ui-lib/src/components/slider/Slider.js
Original file line number Diff line number Diff line change
Expand Up @@ -247,8 +247,8 @@ export default class Slider extends PureComponent {
vertical,
reverse
)
const value = percentToValue(percent, min, max)

const value = percentToValue(percent, min, max)
this.emitChange(event, value, () => this.setToResetState())
}

Expand All @@ -263,52 +263,60 @@ export default class Slider extends PureComponent {
this.emitChange(event, clamp(value + (step || 1), min, max))
}

onTouchStartHandler = event => {
this.setState({
_listenForPropChanges: false,
currentState: 'activated'
})

onMouseDownHandler = event => {
if (typeof document !== 'undefined') {
document.body.addEventListener('touchend', this.onMouseUpHandler)
}

if (typeof this.props.on_drag_start === 'function') {
dispatchCustomElementEvent(this, 'on_drag_start', {
event
})
try {
document.body.addEventListener(
'touchmove',
this.onTouchMoveHandler
)
document.body.addEventListener('touchend', this.onTouchEndHandler)
document.body.addEventListener(
'mousemove',
this.onMouseMoveHandler
)
document.body.addEventListener('mouseup', this.onMouseUpHandler)
} catch (e) {
console.warn(e)
}
}
}

onMouseDownHandler = event => {
this.setState({
_listenForPropChanges: false,
currentState: 'activated'
})

if (typeof document !== 'undefined') {
document.body.addEventListener('mousemove', this.onMouseMoveHandler)
document.body.addEventListener('mouseup', this.onMouseUpHandler)
}

if (typeof this.props.on_drag_start === 'function') {
dispatchCustomElementEvent(this, 'on_drag_start', {
event
})
}
}

onTouchEndHandler = event => this.onMouseUpHandler(event)
onMouseUpHandler = event => {
this.setState({ _listenForPropChanges: false, currentState: 'normal' })

if (typeof document !== 'undefined') {
document.body.removeEventListener(
'mousemove',
this.onMouseMoveHandler
)
document.body.removeEventListener('mouseup', this.onMouseUpHandler)
try {
document.body.removeEventListener(
'touchmove',
this.onTouchMoveHandler
)
document.body.removeEventListener(
'touchend',
this.onTouchEndHandler
)
document.body.removeEventListener(
'mousemove',
this.onMouseMoveHandler
)
document.body.removeEventListener('mouseup', this.onMouseUpHandler)
} catch (e) {
console.warn(e)
}
}

this.setState({ _listenForPropChanges: false, currentState: 'normal' })

if (typeof this.props.on_drag_end === 'function') {
dispatchCustomElementEvent(this, 'on_drag_end', {
event
Expand All @@ -324,6 +332,7 @@ export default class Slider extends PureComponent {
})
}

onTouchMoveHandler = event => this.onMouseMoveHandler(event)
onMouseMoveHandler = event => {
let elem = this._trackRef.current

Expand Down Expand Up @@ -394,39 +403,32 @@ export default class Slider extends PureComponent {
_listenForPropChanges: false,
currentState: 'normal'
}),
10
100
)
}
)
}

componentDidMount() {
if (
(isTouchDevice() || isTrue(this.props.use_scrollwheel)) &&
this._trackRef.current
) {
this._trackRef.current.addEventListener(
'touchstart',
this.preventPageScrolling,
{ passive: false }
)

const { min, max, reverse, vertical } = this.state
this._trackRef.current.addEventListener('wheel', event => {
event.preventDefault()
// Could be handy to use: Math.sign(event.deltaY)
this.emitChange(
event,
clamp(
this.state.value +
((!vertical && reverse) || (vertical && !reverse)
? -event.deltaY / 10
: event.deltaY / 10),
min,
max
if (this._trackRef.current) {
if (isTrue(this.props.use_scrollwheel)) {
const { min, max, reverse, vertical } = this.state
this._trackRef.current.addEventListener('wheel', event => {
event.preventDefault()
// Could be handy to use: Math.sign(event.deltaY)
this.emitChange(
event,
clamp(
this.state.value +
((!vertical && reverse) || (vertical && !reverse)
? -event.deltaY / 10
: event.deltaY / 10),
min,
max
)
)
)
})
})
}
}

if (typeof this.props.on_init === 'function') {
Expand All @@ -438,25 +440,28 @@ export default class Slider extends PureComponent {
}

componentWillUnmount() {
if (this._trackRef.current) {
this._trackRef.current.removeEventListener(
'touchstart',
this.preventPageScrolling,
{ passive: false }
)
}
if (typeof document !== 'undefined') {
document.body.removeEventListener(
'mousemove',
this.onMouseMoveHandler
)
document.body.removeEventListener('mouseup', this.onMouseUpHandler)
try {
document.body.removeEventListener(
'touchmove',
this.onTouchMoveHandler
)
document.body.removeEventListener(
'touchend',
this.onTouchEndHandler
)
document.body.removeEventListener(
'mousemove',
this.onMouseMoveHandler
)
document.body.removeEventListener('mouseup', this.onMouseUpHandler)
} catch (e) {
console.warn(e)
}
}
clearTimeout(this.resetStateTimeoutId)
}

preventPageScrolling = event => event.preventDefault()

render() {
const { currentState, value } = this.state

Expand Down Expand Up @@ -534,11 +539,10 @@ export default class Slider extends PureComponent {
'dnb-slider__track',
currentState && `dnb-slider__state--${currentState}`
),
onMouseDown: this.onClickHandler,
onMouseDownCapture: this.onMouseDownHandler,
onTouchStart: this.onClickHandler,
onTouchStartCapture: this.onTouchStartHandler,
onTouchMove: this.onMouseMoveHandler
onTouchStartCapture: this.onMouseDownHandler,
onMouseDown: this.onClickHandler,
onMouseDownCapture: this.onMouseDownHandler
}

const rangeParams = {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -185,7 +185,6 @@ exports[`Slider component have to match snapshot 1`] = `
id="id"
onMouseDown={[Function]}
onMouseDownCapture={[Function]}
onTouchMove={[Function]}
onTouchStart={[Function]}
onTouchStartCapture={[Function]}
>
Expand Down Expand Up @@ -918,6 +917,7 @@ legend.dnb-form-label {
display: inline-flex;
height: var(--slider-thumb-size); }
.dnb-slider__track {
touch-action: none;
position: relative;
flex: 1;
margin: 0 calc(var(--slider-space) * 1.5);
Expand Down
3 changes: 3 additions & 0 deletions packages/dnb-ui-lib/src/components/slider/style/_slider.scss
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,9 @@
}

&__track {
// make sure we do not alow page scroll on touch devices
touch-action: none;

position: relative;
flex: 1;

Expand Down

0 comments on commit 4171c3a

Please sign in to comment.