1
0
mirror of https://github.com/ianstormtaylor/slate.git synced 2025-08-17 20:51:20 +02:00

Call scrollToSelection on selection update. (#1134)

This commit is contained in:
AlbertHilb
2017-09-18 18:22:01 +02:00
committed by Ian Storm Taylor
parent ee2c4e6bc7
commit fd7981782c
2 changed files with 3 additions and 64 deletions

View File

@@ -17,6 +17,7 @@ import getHtmlFromNativePaste from '../utils/get-html-from-native-paste'
import getPoint from '../utils/get-point'
import getTransferData from '../utils/get-transfer-data'
import setTransferData from '../utils/set-transfer-data'
import scrollToSelection from '../utils/scroll-to-selection'
import { IS_FIREFOX, IS_MAC, IS_IE } from '../constants/environment'
/**
@@ -165,6 +166,8 @@ class Content extends React.Component {
native.addRange(range)
if (!isCollapsed) extendSelection(native, focus.node, focus.offset)
scrollToSelection(native)
// Then unset the `isSelecting` flag after a delay.
setTimeout(() => {
// COMPAT: In Firefox, it's not enough to create a range, you also need to

View File

@@ -2,15 +2,12 @@
import Base64 from 'slate-base64-serializer'
import Debug from 'debug'
import React from 'react'
import ReactDOM from 'react-dom'
import SlateTypes from 'slate-prop-types'
import Types from 'prop-types'
import getWindow from 'get-window'
import TRANSFER_TYPES from '../constants/transfer-types'
import Leaf from './leaf'
import Void from './void'
import scrollToSelection from '../utils/scroll-to-selection'
import setTransferData from '../utils/set-transfer-data'
/**
@@ -143,67 +140,6 @@ class Node extends React.Component {
return false
}
/**
* On mount, update the scroll position.
*/
componentDidMount = () => {
this.updateScroll()
}
/**
* After update, update the scroll position if the node's content changed.
*
* @param {Object} prevProps
* @param {Object} prevState
*/
componentDidUpdate = (prevProps, prevState) => {
if (this.props.node != prevProps.node) this.updateScroll()
}
/**
* There is a corner case, that some nodes are unmounted right after they update
* Then, when the timer execute, it will throw the error
* `findDOMNode was called on an unmounted component`
* We should clear the timer from updateScroll here
*/
componentWillUnmount = () => {
clearTimeout(this.scrollTimer)
}
/**
* Update the scroll position after a change as occured if this is a leaf
* block and it has the selection's ending edge. This ensures that scrolling
* matches native `contenteditable` behavior even for cases where the edit is
* not applied natively, like when enter is pressed.
*/
updateScroll = () => {
const { node, state } = this.props
const { selection } = state
// If this isn't a block, or it's a wrapping block, abort.
if (node.kind != 'block') return
if (node.nodes.first().kind == 'block') return
// If the selection is blurred, or this block doesn't contain it, abort.
if (selection.isBlurred) return
if (!selection.hasEndIn(node)) return
// The native selection will be updated after componentDidMount or componentDidUpdate.
// Use setTimeout to queue scrolling to the last when the native selection has been updated to the correct value.
this.scrollTimer = setTimeout(() => {
const el = ReactDOM.findDOMNode(this)
const window = getWindow(el)
const native = window.getSelection()
scrollToSelection(native)
this.debug('updateScroll', el)
})
}
/**
* On drag start, add a serialized representation of the node to the data.
*