summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGilles Debunne <debunne@google.com>2011-03-08 10:21:54 -0800
committerAndroid (Google) Code Review <android-gerrit@google.com>2011-03-08 10:21:54 -0800
commit949d0c8c384437d92fc1432b750da6da59df1fa7 (patch)
tree870dd094812c26bd311a2a72c7e9067be63e53ff
parent055a858562e04c903988d09973accc8aeeece02c (diff)
parentcfc22c533222f0181be7a717fbf721891d3bfd2d (diff)
downloadframeworks_base-949d0c8c384437d92fc1432b750da6da59df1fa7.zip
frameworks_base-949d0c8c384437d92fc1432b750da6da59df1fa7.tar.gz
frameworks_base-949d0c8c384437d92fc1432b750da6da59df1fa7.tar.bz2
Merge "Text handles positions' are correctly updated." into honeycomb-mr1
-rw-r--r--core/java/android/widget/PopupWindow.java2
-rw-r--r--core/java/android/widget/TextView.java226
2 files changed, 99 insertions, 129 deletions
diff --git a/core/java/android/widget/PopupWindow.java b/core/java/android/widget/PopupWindow.java
index 9002b1d..72b70bc 100644
--- a/core/java/android/widget/PopupWindow.java
+++ b/core/java/android/widget/PopupWindow.java
@@ -1039,7 +1039,7 @@ public class PopupWindow {
*
* @return true if the popup is translated upwards to fit on screen
*/
- boolean findDropDownPosition(View anchor, WindowManager.LayoutParams p,
+ private boolean findDropDownPosition(View anchor, WindowManager.LayoutParams p,
int xoff, int yoff) {
anchor.getLocationInWindow(mDrawingLocation);
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java
index 09c1ac5..13b9285f 100644
--- a/core/java/android/widget/TextView.java
+++ b/core/java/android/widget/TextView.java
@@ -4498,8 +4498,6 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
*/
canvas.restore();
-
- updateCursorControllerPositions();
}
private void updateCursorsPositions() {
@@ -4557,15 +4555,7 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
* @hide
*/
protected void updateCursorControllerPositions() {
- // No need to create the controllers if they were not already
- if (mInsertionPointCursorController != null &&
- mInsertionPointCursorController.isShowing()) {
- mInsertionPointCursorController.updatePosition();
- }
- if (mSelectionModifierCursorController != null &&
- mSelectionModifierCursorController.isShowing()) {
- mSelectionModifierCursorController.updatePosition();
- }
+ // TODO remove
}
@Override
@@ -7356,14 +7346,9 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
}
if (isTextEditable() || mTextIsSelectable) {
- if (mScrollX != oldScrollX || mScrollY != oldScrollY) {
+ if (mScrollX != oldScrollX || mScrollY != oldScrollY) { // TODO remove
// Hide insertion anchor while scrolling. Leave selection.
- hideInsertionPointCursorController();
- // No need to create the controller, since there is nothing to update.
- if (mSelectionModifierCursorController != null &&
- mSelectionModifierCursorController.isShowing()) {
- mSelectionModifierCursorController.updatePosition();
- }
+ hideInsertionPointCursorController(); // TODO any motion should hide it
}
if (touchIsFinished) {
@@ -7373,7 +7358,6 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
handled |= imm != null && imm.showSoftInput(this, 0);
}
-
boolean selectAllGotFocus = mSelectAllOnFocus && didTouchFocusSelect();
if (!selectAllGotFocus && hasSelection()) {
startSelectionActionMode();
@@ -8653,26 +8637,31 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
}
}
- private class HandleView extends View implements ViewTreeObserver.OnScrollChangedListener {
+ private class HandleView extends View implements ViewTreeObserver.OnPreDrawListener {
private Drawable mDrawable;
- private final ScrollingPopupWindow mContainer;
- private int mPositionX;
- private int mPositionY;
+ private final PopupWindow mContainer;
+ // Position with respect to the parent TextView
+ private int mPositionX, mPositionY;
private final CursorController mController;
private boolean mIsDragging;
- private float mTouchToWindowOffsetX;
- private float mTouchToWindowOffsetY;
+ // Offset from touch position to mPosition
+ private float mTouchToWindowOffsetX, mTouchToWindowOffsetY;
private float mHotspotX;
// Offsets the hotspot point up, so that cursor is not hidden by the finger when moving up
private float mTouchOffsetY;
// Where the touch position should be on the handle to ensure a maximum cursor visibility
private float mIdealVerticalOffset;
- private int mLastParentX;
- private int mLastParentY;
+ // Parent's (TextView) position in window
+ private int mLastParentX, mLastParentY;
private float mDownPositionX, mDownPositionY;
+ // PopupWindow container absolute position with respect to the enclosing window
private int mContainerPositionX, mContainerPositionY;
- private long mTouchTimer;
+ // Visible or not (scrolled off screen), whether or not this handle should be visible
+ private boolean mIsActive = false;
+ // The insertion handle can have an associated PastePopupMenu
private boolean mIsInsertionHandle = false;
+ // Used to detect taps on the insertion handle, which will affect the PastePopupMenu
+ private long mTouchTimer;
private PastePopupMenu mPastePopupWindow;
// Touch-up filter: number of previous positions remembered
@@ -8684,12 +8673,12 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
private int mPreviousOffsetIndex = 0;
private int mNumberPreviousOffsets = 0;
- public void startTouchUpFilter(int offset) {
+ private void startTouchUpFilter(int offset) {
mNumberPreviousOffsets = 0;
addPositionToTouchUpFilter(offset);
}
- public void addPositionToTouchUpFilter(int offset) {
+ private void addPositionToTouchUpFilter(int offset) {
if (mNumberPreviousOffsets > 0 &&
mPreviousOffsets[mPreviousOffsetIndex] == offset) {
// Make sure only actual changes of position are recorded.
@@ -8702,7 +8691,7 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
mNumberPreviousOffsets++;
}
- public void filterOnTouchUp() {
+ private void filterOnTouchUp() {
final long now = SystemClock.uptimeMillis();
int i = 0;
int index = mPreviousOffsetIndex;
@@ -8725,16 +8714,17 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
public HandleView(CursorController controller, int pos) {
super(TextView.this.mContext);
mController = controller;
- mContainer = new ScrollingPopupWindow(TextView.this.mContext, null,
+ mContainer = new PopupWindow(TextView.this.mContext, null,
com.android.internal.R.attr.textSelectHandleWindowStyle);
mContainer.setSplitTouchEnabled(true);
mContainer.setClippingEnabled(false);
mContainer.setWindowLayoutType(WindowManager.LayoutParams.TYPE_APPLICATION_SUB_PANEL);
+ mContainer.setContentView(this);
- setOrientation(pos);
+ setPosition(pos);
}
- public void setOrientation(int pos) {
+ private void setPosition(int pos) {
int handleWidth;
switch (pos) {
case LEFT: {
@@ -8774,38 +8764,48 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
}
final int handleHeight = mDrawable.getIntrinsicHeight();
-
mTouchOffsetY = -0.3f * handleHeight;
mIdealVerticalOffset = 0.7f * handleHeight;
+
invalidate();
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- setMeasuredDimension(mDrawable.getIntrinsicWidth(),
- mDrawable.getIntrinsicHeight());
+ setMeasuredDimension(mDrawable.getIntrinsicWidth(), mDrawable.getIntrinsicHeight());
}
public void show() {
- if (!isPositionVisible()) {
- hide();
- return;
- }
- mContainer.setContentView(this);
- mContainerPositionX = mPositionX;
- mContainerPositionY = mPositionY - TextView.this.getHeight();
- mContainer.showAsDropDown(TextView.this, mContainerPositionX, mContainerPositionY);
+ updateContainerPosition();
+ if (isShowing()) {
+ mContainer.update(mContainerPositionX, mContainerPositionY,
+ mRight - mLeft, mBottom - mTop);
- // Hide paste view when handle is moved on screen.
- hidePastePopupWindow();
+ hidePastePopupWindow();
+ } else {
+ mContainer.showAtLocation(TextView.this, 0,
+ mContainerPositionX, mContainerPositionY);
+
+ mIsActive = true;
+
+ ViewTreeObserver vto = TextView.this.getViewTreeObserver();
+ vto.addOnPreDrawListener(this);
+ }
}
- public void hide() {
+ private void dismiss() {
mIsDragging = false;
mContainer.dismiss();
hidePastePopupWindow();
+ }
+
+ public void hide() {
+ dismiss();
+
+ mIsActive = false;
+
ViewTreeObserver vto = TextView.this.getViewTreeObserver();
- vto.removeOnScrollChangedListener(this);
+ vto.removeOnPreDrawListener(this);
}
public boolean isShowing() {
@@ -8856,44 +8856,59 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
private void moveTo(int x, int y) {
mPositionX = x - TextView.this.mScrollX;
mPositionY = y - TextView.this.mScrollY;
- if (isPositionVisible()) {
- int[] coords = null;
- if (mContainer.isShowing()) {
- final int containerPositionX = mPositionX;
- final int containerPositionY = mPositionY - TextView.this.getHeight();
-
- if (containerPositionX != mContainerPositionX ||
- containerPositionY != mContainerPositionY) {
- mContainerPositionX = containerPositionX;
- mContainerPositionY = containerPositionY;
-
- mContainer.update(TextView.this, mContainerPositionX, mContainerPositionY,
- mRight - mLeft, mBottom - mTop);
-
- // Hide paste popup window as soon as a scroll occurs.
- hidePastePopupWindow();
- }
- } else {
- show();
+
+ if (mIsDragging) {
+ TextView.this.getLocationInWindow(mTempCoords);
+ if (mTempCoords[0] != mLastParentX || mTempCoords[1] != mLastParentY) {
+ mTouchToWindowOffsetX += mTempCoords[0] - mLastParentX;
+ mTouchToWindowOffsetY += mTempCoords[1] - mLastParentY;
+ mLastParentX = mTempCoords[0];
+ mLastParentY = mTempCoords[1];
}
+ // Hide paste popup window as soon as the handle is dragged.
+ hidePastePopupWindow();
+ }
+ }
- if (mIsDragging) {
- if (coords == null) {
- coords = mTempCoords;
- TextView.this.getLocationInWindow(coords);
+ /**
+ * Updates the global container's position.
+ * @return whether or not the position has actually changed
+ */
+ private boolean updateContainerPosition() {
+ // TODO Prevent this using different HandleView subclasses
+ mController.updateOffset(this, mController.getCurrentOffset(this));
+ TextView.this.getLocationInWindow(mTempCoords);
+ final int containerPositionX = mTempCoords[0] + mPositionX;
+ final int containerPositionY = mTempCoords[1] + mPositionY;
+
+ if (containerPositionX != mContainerPositionX ||
+ containerPositionY != mContainerPositionY) {
+ mContainerPositionX = containerPositionX;
+ mContainerPositionY = containerPositionY;
+ return true;
+ }
+ return false;
+ }
+
+ public boolean onPreDraw() {
+ if (updateContainerPosition()) {
+ if (isPositionVisible()) {
+ mContainer.update(mContainerPositionX, mContainerPositionY,
+ mRight - mLeft, mBottom - mTop);
+
+ if (mIsActive && !isShowing()) {
+ show();
}
- if (coords[0] != mLastParentX || coords[1] != mLastParentY) {
- mTouchToWindowOffsetX += coords[0] - mLastParentX;
- mTouchToWindowOffsetY += coords[1] - mLastParentY;
- mLastParentX = coords[0];
- mLastParentY = coords[1];
+ } else {
+ if (isShowing()) {
+ dismiss();
}
- // Hide paste popup window as soon as the handle is dragged.
- hidePastePopupWindow();
}
- } else {
- hide();
+
+ // Hide paste popup as soon as the view is scrolled or moved
+ hidePastePopupWindow();
}
+ return true;
}
@Override
@@ -8979,7 +8994,7 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
return mIsDragging;
}
- void positionAtCursor(final int offset) {
+ void positionAtCursor(int offset) {
addPositionToTouchUpFilter(offset);
final int width = mDrawable.getIntrinsicWidth();
final int height = mDrawable.getIntrinsicHeight();
@@ -9013,50 +9028,6 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
mPastePopupWindow.hide();
}
}
-
- /**
- * A popup window, attached to a view, and that listens to scroll events in its anchors'
- * view hierarchy, so that it is automatically moved on such events.
- */
- private class ScrollingPopupWindow extends PopupWindow {
-
- private int[] mDrawingLocations = new int[2];
-
- public ScrollingPopupWindow(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- }
-
- @Override
- public boolean findDropDownPosition(View anchor, WindowManager.LayoutParams p,
- int xoff, int yoff) {
- anchor.getLocationInWindow(mDrawingLocations);
- p.x = mDrawingLocations[0] + xoff;
- p.y = mDrawingLocations[1] + anchor.getHeight() + yoff;
-
- // Hide paste popup as soon as the view is scrolled.
- hidePastePopupWindow();
-
- if (!isPositionVisible()) {
- dismiss();
- onHandleBecomeInvisible();
- }
-
- return false;
- }
- }
-
- public void onScrollChanged() {
- if (isPositionVisible()) {
- show();
- ViewTreeObserver vto = TextView.this.getViewTreeObserver();
- vto.removeOnScrollChangedListener(this);
- }
- }
-
- public void onHandleBecomeInvisible() {
- ViewTreeObserver vto = TextView.this.getViewTreeObserver();
- vto.addOnScrollChangedListener(this);
- }
}
private class InsertionPointCursorController implements CursorController {
@@ -9074,7 +9045,7 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
}
public void show(int delayBeforePaste) {
- updatePosition();
+ getHandle().show();
hideDelayed();
removePastePopupCallback();
final long durationSinceCutOrCopy = SystemClock.uptimeMillis() - sLastCutOrCopyTime;
@@ -9213,7 +9184,6 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener
if (mEndHandle == null) mEndHandle = new HandleView(this, HandleView.RIGHT);
mIsShowing = true;
- updatePosition();
mStartHandle.show();
mEndHandle.show();