am 46b70388: am b300d31b: Merge "Text selection: fix some issues with drag accelerator" into mnc-dev
* commit '46b7038811259a22c5494c0420185836cc4d3e76': Text selection: fix some issues with drag accelerator
This commit is contained in:
@@ -3495,6 +3495,10 @@ public class Editor {
|
|||||||
mIdealVerticalOffset = 0.7f * handleHeight;
|
mIdealVerticalOffset = 0.7f * handleHeight;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public float getIdealVerticalOffset() {
|
||||||
|
return mIdealVerticalOffset;
|
||||||
|
}
|
||||||
|
|
||||||
protected void updateDrawable() {
|
protected void updateDrawable() {
|
||||||
final int offset = getCurrentCursorOffset();
|
final int offset = getCurrentCursorOffset();
|
||||||
final boolean isRtlCharAtOffset = mTextView.getLayout().isRtlCharAt(offset);
|
final boolean isRtlCharAtOffset = mTextView.getLayout().isRtlCharAt(offset);
|
||||||
@@ -4279,6 +4283,7 @@ public class Editor {
|
|||||||
private int mStartOffset = -1;
|
private int mStartOffset = -1;
|
||||||
// Indicates whether the user is selecting text and using the drag accelerator.
|
// Indicates whether the user is selecting text and using the drag accelerator.
|
||||||
private boolean mDragAcceleratorActive;
|
private boolean mDragAcceleratorActive;
|
||||||
|
private boolean mHaventMovedEnoughToStartDrag;
|
||||||
|
|
||||||
SelectionModifierCursorController() {
|
SelectionModifierCursorController() {
|
||||||
resetTouchOffsets();
|
resetTouchOffsets();
|
||||||
@@ -4343,19 +4348,20 @@ public class Editor {
|
|||||||
public void onTouchEvent(MotionEvent event) {
|
public void onTouchEvent(MotionEvent event) {
|
||||||
// This is done even when the View does not have focus, so that long presses can start
|
// This is done even when the View does not have focus, so that long presses can start
|
||||||
// selection and tap can move cursor from this tap position.
|
// selection and tap can move cursor from this tap position.
|
||||||
|
final float eventX = event.getX();
|
||||||
|
final float eventY = event.getY();
|
||||||
switch (event.getActionMasked()) {
|
switch (event.getActionMasked()) {
|
||||||
case MotionEvent.ACTION_DOWN:
|
case MotionEvent.ACTION_DOWN:
|
||||||
final float x = event.getX();
|
|
||||||
final float y = event.getY();
|
|
||||||
|
|
||||||
// Remember finger down position, to be able to start selection from there.
|
// Remember finger down position, to be able to start selection from there.
|
||||||
mMinTouchOffset = mMaxTouchOffset = mTextView.getOffsetForPosition(x, y);
|
mMinTouchOffset = mMaxTouchOffset = mTextView.getOffsetForPosition(
|
||||||
|
eventX, eventY);
|
||||||
|
|
||||||
// Double tap detection
|
// Double tap detection
|
||||||
if (mGestureStayedInTapRegion) {
|
if (mGestureStayedInTapRegion) {
|
||||||
if (mDoubleTap) {
|
if (mDoubleTap) {
|
||||||
final float deltaX = x - mDownPositionX;
|
final float deltaX = eventX - mDownPositionX;
|
||||||
final float deltaY = y - mDownPositionY;
|
final float deltaY = eventY - mDownPositionY;
|
||||||
final float distanceSquared = deltaX * deltaX + deltaY * deltaY;
|
final float distanceSquared = deltaX * deltaX + deltaY * deltaY;
|
||||||
|
|
||||||
ViewConfiguration viewConfiguration = ViewConfiguration.get(
|
ViewConfiguration viewConfiguration = ViewConfiguration.get(
|
||||||
@@ -4363,16 +4369,17 @@ public class Editor {
|
|||||||
int doubleTapSlop = viewConfiguration.getScaledDoubleTapSlop();
|
int doubleTapSlop = viewConfiguration.getScaledDoubleTapSlop();
|
||||||
boolean stayedInArea = distanceSquared < doubleTapSlop * doubleTapSlop;
|
boolean stayedInArea = distanceSquared < doubleTapSlop * doubleTapSlop;
|
||||||
|
|
||||||
if (stayedInArea && isPositionOnText(x, y)) {
|
if (stayedInArea && isPositionOnText(eventX, eventY)) {
|
||||||
startSelectionActionModeWithSelectionAndStartDrag();
|
startSelectionActionModeWithSelectionAndStartDrag();
|
||||||
mDiscardNextActionUp = true;
|
mDiscardNextActionUp = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
mDownPositionX = x;
|
mDownPositionX = eventX;
|
||||||
mDownPositionY = y;
|
mDownPositionY = eventY;
|
||||||
mGestureStayedInTapRegion = true;
|
mGestureStayedInTapRegion = true;
|
||||||
|
mHaventMovedEnoughToStartDrag = true;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MotionEvent.ACTION_POINTER_DOWN:
|
case MotionEvent.ACTION_POINTER_DOWN:
|
||||||
@@ -4386,18 +4393,24 @@ public class Editor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case MotionEvent.ACTION_MOVE:
|
case MotionEvent.ACTION_MOVE:
|
||||||
final ViewConfiguration viewConfiguration = ViewConfiguration.get(
|
final ViewConfiguration viewConfig = ViewConfiguration.get(
|
||||||
mTextView.getContext());
|
mTextView.getContext());
|
||||||
|
final int touchSlop = viewConfig.getScaledTouchSlop();
|
||||||
|
|
||||||
if (mGestureStayedInTapRegion) {
|
if (mGestureStayedInTapRegion || mHaventMovedEnoughToStartDrag) {
|
||||||
final float deltaX = event.getX() - mDownPositionX;
|
final float deltaX = eventX - mDownPositionX;
|
||||||
final float deltaY = event.getY() - mDownPositionY;
|
final float deltaY = eventY - mDownPositionY;
|
||||||
final float distanceSquared = deltaX * deltaX + deltaY * deltaY;
|
final float distanceSquared = deltaX * deltaX + deltaY * deltaY;
|
||||||
|
|
||||||
int doubleTapTouchSlop = viewConfiguration.getScaledDoubleTapTouchSlop();
|
if (mGestureStayedInTapRegion) {
|
||||||
|
int doubleTapTouchSlop = viewConfig.getScaledDoubleTapTouchSlop();
|
||||||
if (distanceSquared > doubleTapTouchSlop * doubleTapTouchSlop) {
|
mGestureStayedInTapRegion =
|
||||||
mGestureStayedInTapRegion = false;
|
distanceSquared <= doubleTapTouchSlop * doubleTapTouchSlop;
|
||||||
|
}
|
||||||
|
if (mHaventMovedEnoughToStartDrag) {
|
||||||
|
// We don't start dragging until the user has moved enough.
|
||||||
|
mHaventMovedEnoughToStartDrag =
|
||||||
|
distanceSquared <= touchSlop * touchSlop;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -4407,56 +4420,28 @@ public class Editor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (mStartOffset != -1) {
|
if (mStartOffset != -1) {
|
||||||
final int rawOffset = mTextView.getOffsetForPosition(event.getX(),
|
if (!mHaventMovedEnoughToStartDrag) {
|
||||||
event.getY());
|
// Offset the finger by the same vertical offset as the handles. This
|
||||||
int offset = rawOffset;
|
// improves visibility of the content being selected by shifting
|
||||||
|
// the finger below the content.
|
||||||
// We don't start "dragging" until the user is past the initial word that
|
final float fingerOffset = (mStartHandle != null)
|
||||||
// gets selected on long press.
|
? mStartHandle.getIdealVerticalOffset()
|
||||||
int firstWordStart = getWordStart(mStartOffset);
|
: touchSlop;
|
||||||
int firstWordEnd = getWordEnd(mStartOffset);
|
int offset =
|
||||||
if (offset > firstWordEnd || offset < firstWordStart) {
|
mTextView.getOffsetForPosition(eventX, eventY - fingerOffset);
|
||||||
|
int startOffset;
|
||||||
// Basically the goal in the below code is to have the highlight be
|
// Snap to word boundaries.
|
||||||
// offset so that your finger isn't covering the end point.
|
|
||||||
int fingerOffset = viewConfiguration.getScaledTouchSlop();
|
|
||||||
float mx = event.getX();
|
|
||||||
float my = event.getY();
|
|
||||||
if (mx > fingerOffset) mx -= fingerOffset;
|
|
||||||
if (my > fingerOffset) my -= fingerOffset;
|
|
||||||
offset = mTextView.getOffsetForPosition(mx, my);
|
|
||||||
|
|
||||||
// Perform the check for closeness at edge of view, if we're very close
|
|
||||||
// don't adjust the offset to be in front of the finger - otherwise the
|
|
||||||
// user can't select words at the edge.
|
|
||||||
if (mTextView.getWidth() - fingerOffset > mx) {
|
|
||||||
// We're going by word, so we need to make sure that the offset
|
|
||||||
// that we get is within this, so we'll get the previous boundary.
|
|
||||||
final WordIterator wordIterator = getWordIteratorWithText();
|
|
||||||
|
|
||||||
final int precedingOffset = wordIterator.preceding(offset);
|
|
||||||
if (mStartOffset < offset) {
|
if (mStartOffset < offset) {
|
||||||
// Expanding with bottom handle, in this case the selection end
|
// Expanding with end handle.
|
||||||
// is before the finger.
|
offset = getWordEnd(offset);
|
||||||
offset = Math.max(precedingOffset - 1, 0);
|
startOffset = getWordStart(mStartOffset);
|
||||||
} else {
|
} else {
|
||||||
// Expand with the start handle, in this case the selection
|
// Expanding with start handle.
|
||||||
// start is before the finger.
|
offset = getWordStart(offset);
|
||||||
if (precedingOffset == WordIterator.DONE) {
|
startOffset = getWordEnd(mStartOffset);
|
||||||
offset = 0;
|
|
||||||
} else {
|
|
||||||
offset = wordIterator.preceding(precedingOffset);
|
|
||||||
}
|
}
|
||||||
}
|
Selection.setSelection((Spannable) mTextView.getText(),
|
||||||
}
|
startOffset, offset);
|
||||||
if (offset == WordIterator.DONE)
|
|
||||||
offset = rawOffset;
|
|
||||||
|
|
||||||
// Need to adjust start offset based on direction of movement.
|
|
||||||
int newStart = mStartOffset < offset ? getWordStart(mStartOffset)
|
|
||||||
: getWordEnd(mStartOffset);
|
|
||||||
Selection.setSelection((Spannable) mTextView.getText(), newStart,
|
|
||||||
offset);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|||||||
Reference in New Issue
Block a user