summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorYorke Lee <yorkelee@google.com>2014-01-16 11:26:46 -0800
committerYorke Lee <yorkelee@google.com>2014-02-20 12:24:36 -0800
commit3cefcc69c10ab12bd782a0b53779dbd1cc0e2aa1 (patch)
treee627f324ef1be14d2ac00bafe043d8f28294d575 /src
parent28ded60d6aa23314d2cfca9ccca1e5bf731508e4 (diff)
Add drag to remove for favorites in Dialer
* Add remove view in dialtacts_activity.xml, and rearrange layout slightly so that it takes up the same position in the layout as the search view container. Contacts that are dragged to this remove view will be unstarred and unpinned. * Add drag event logic to the Remove View, so that when the user hovers a contact over it, the UI will continue to respond. Previously, only the PhoneFavoritesListView would detect touch events. * Refactor DragDropController and OnDragDropListener into separate classes. DragDropController performs the work of receiving drag/drop events from multiple views, combining them, and then firing off callbacks as appropriate to OnDragDropListeners. Each OnDragDropListener can then update their UI or internal data model as necessary in response to the callbacks. OnDragDropListener <---------------------------------------- ^ | | | DialtactsActivity ---------------> RemoveView | | | | v | | callbacks PhoneFavoriteListFragment |drag events | | | | v v | PhoneFavoriteListView ------------> DragController-------- drag events | | callbacks v PhoneFavoritesTileAdapter --> OnDragDropListener * While in here, add a content description for the clear search button Change-Id: I044ad1c5aa42c7686bde6bf5074095a4fe879bde
Diffstat (limited to 'src')
-rw-r--r--src/com/android/dialer/DialtactsActivity.java59
-rw-r--r--src/com/android/dialer/list/DragDropController.java71
-rw-r--r--src/com/android/dialer/list/OnDragDropListener.java41
-rw-r--r--src/com/android/dialer/list/PhoneFavoriteFragment.java15
-rw-r--r--src/com/android/dialer/list/PhoneFavoriteListView.java166
-rw-r--r--src/com/android/dialer/list/PhoneFavoritesTileAdapter.java26
-rw-r--r--src/com/android/dialer/list/RemoveView.java90
7 files changed, 368 insertions, 100 deletions
diff --git a/src/com/android/dialer/DialtactsActivity.java b/src/com/android/dialer/DialtactsActivity.java
index 0c0fcdafe..227cd8eca 100644
--- a/src/com/android/dialer/DialtactsActivity.java
+++ b/src/com/android/dialer/DialtactsActivity.java
@@ -22,7 +22,6 @@ import android.animation.AnimatorListenerAdapter;
import android.app.Activity;
import android.app.Fragment;
import android.app.FragmentManager;
-import android.app.FragmentManager.BackStackEntry;
import android.app.FragmentTransaction;
import android.content.ActivityNotFoundException;
import android.content.Context;
@@ -50,8 +49,6 @@ import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.View.OnFocusChangeListener;
import android.view.inputmethod.InputMethodManager;
import android.widget.AbsListView.OnScrollListener;
import android.widget.EditText;
@@ -70,9 +67,13 @@ import com.android.dialer.dialpad.SmartDialNameMatcher;
import com.android.dialer.dialpad.SmartDialPrefix;
import com.android.dialer.interactions.PhoneNumberInteraction;
import com.android.dialer.list.AllContactsActivity;
+import com.android.dialer.list.DragDropController;
+import com.android.dialer.list.OnDragDropListener;
import com.android.dialer.list.OnListFragmentScrolledListener;
import com.android.dialer.list.PhoneFavoriteFragment;
+import com.android.dialer.list.PhoneFavoriteTileView;
import com.android.dialer.list.RegularSearchFragment;
+import com.android.dialer.list.RemoveView;
import com.android.dialer.list.SearchFragment;
import com.android.dialer.list.SmartDialSearchFragment;
import com.android.dialerbind.DatabaseHelperManager;
@@ -88,7 +89,9 @@ public class DialtactsActivity extends TransactionSafeActivity implements View.O
DialpadFragment.OnDialpadQueryChangedListener, PopupMenu.OnMenuItemClickListener,
OnListFragmentScrolledListener,
DialpadFragment.OnDialpadFragmentStartedListener,
- PhoneFavoriteFragment.OnShowAllContactsListener {
+ PhoneFavoriteFragment.OnShowAllContactsListener,
+ PhoneFavoriteFragment.HostInterface,
+ OnDragDropListener {
private static final String TAG = "DialtactsActivity";
public static final boolean DEBUG = false;
@@ -122,6 +125,8 @@ public class DialtactsActivity extends TransactionSafeActivity implements View.O
private static final int ACTIVITY_REQUEST_CODE_VOICE_SEARCH = 1;
+ private static final int FADE_ANIMATION_DURATION = 200;
+
private String mFilterText;
/**
@@ -168,6 +173,7 @@ public class DialtactsActivity extends TransactionSafeActivity implements View.O
*/
private boolean mFirstLaunch;
private View mSearchViewContainer;
+ private RemoveView mRemoveViewContainer;
private View mSearchViewCloseButton;
private View mVoiceSearchButton;
private EditText mSearchView;
@@ -312,6 +318,7 @@ public class DialtactsActivity extends TransactionSafeActivity implements View.O
mBottomPaddingView = findViewById(R.id.dialtacts_bottom_padding);
mFragmentsFrame = findViewById(R.id.dialtacts_frame);
mActionBar = findViewById(R.id.fake_action_bar);
+ mRemoveViewContainer = (RemoveView) findViewById(R.id.remove_view_container);
prepareSearchView();
if (UI.FILTER_CONTACTS_ACTION.equals(intent.getAction())
@@ -977,4 +984,48 @@ public class DialtactsActivity extends TransactionSafeActivity implements View.O
PackageManager.MATCH_DEFAULT_ONLY);
return resolveInfo != null && resolveInfo.size() > 0;
}
+
+ @Override
+ public void onDragStarted(int itemIndex, int x, int y, PhoneFavoriteTileView view) {
+ crossfadeViews(mRemoveViewContainer, mSearchViewContainer, FADE_ANIMATION_DURATION);
+ }
+
+ @Override
+ public void onDragHovered(int itemIndex, int x, int y) {}
+
+ @Override
+ public void onDragFinished(int x, int y) {
+ crossfadeViews(mSearchViewContainer, mRemoveViewContainer, FADE_ANIMATION_DURATION);
+ }
+
+ @Override
+ public void onDroppedOnRemove() {}
+
+ /**
+ * Allows the PhoneFavoriteFragment to attach the drag controller to mRemoveViewContainer
+ * once it has been attached to the activity.
+ */
+ @Override
+ public void setDragDropController(DragDropController dragController) {
+ mRemoveViewContainer.setDragDropController(dragController);
+ }
+
+ /**
+ * Crossfades two views so that the first one appears while the other one is fading
+ * out of view.
+ */
+ private void crossfadeViews(final View fadeIn, final View fadeOut, int duration) {
+ fadeOut.animate().alpha(0).setDuration(duration)
+ .setListener(new AnimatorListenerAdapter() {
+ @Override
+ public void onAnimationEnd(Animator animation) {
+ fadeOut.setVisibility(View.GONE);
+ }
+ });
+
+ fadeIn.setVisibility(View.VISIBLE);
+ fadeIn.setAlpha(0);
+ fadeIn.animate().alpha(1).setDuration(FADE_ANIMATION_DURATION)
+ .setListener(null);
+ }
}
diff --git a/src/com/android/dialer/list/DragDropController.java b/src/com/android/dialer/list/DragDropController.java
new file mode 100644
index 000000000..399cd099b
--- /dev/null
+++ b/src/com/android/dialer/list/DragDropController.java
@@ -0,0 +1,71 @@
+package com.android.dialer.list;
+
+import android.view.View;
+
+import com.android.dialer.list.PhoneFavoritesTileAdapter.ContactTileRow;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Class that handles and combines drag events generated from multiple views, and then fires
+ * off events to any OnDragDropListeners that have registered for callbacks.
+ */
+public class DragDropController {
+ private List<OnDragDropListener> mOnDragDropListeners = new ArrayList<OnDragDropListener>();
+
+ /**
+ * @return True if the drag is started, false if the drag is cancelled for some reason.
+ */
+ boolean handleDragStarted(int x, int y, ContactTileRow tileRow) {
+ final PhoneFavoriteTileView tileView =
+ (PhoneFavoriteTileView) tileRow.getViewAtPosition(x, y);
+
+ final int itemIndex = tileRow.getItemIndex(x, y);
+ if (itemIndex != -1 && !mOnDragDropListeners.isEmpty()) {
+ for (int i = 0; i < mOnDragDropListeners.size(); i++) {
+ mOnDragDropListeners.get(i).onDragStarted(itemIndex, x, y, tileView);
+ }
+ }
+
+ return true;
+ }
+
+ public void handleDragHovered(int x, int y, View view) {
+ int itemIndex;
+ if (!(view instanceof ContactTileRow)) {
+ itemIndex = -1;
+ } else {
+ final ContactTileRow tile = (ContactTileRow) view;
+ itemIndex = tile.getItemIndex(x, y);
+ }
+ for (int i = 0; i < mOnDragDropListeners.size(); i++) {
+ mOnDragDropListeners.get(i).onDragHovered(itemIndex, x, y);
+ }
+ }
+
+ public void handleDragFinished(int x, int y, boolean isRemoveView) {
+ if (isRemoveView) {
+ for (int i = 0; i < mOnDragDropListeners.size(); i++) {
+ mOnDragDropListeners.get(i).onDroppedOnRemove();
+ }
+ }
+
+ for (int i = 0; i < mOnDragDropListeners.size(); i++) {
+ mOnDragDropListeners.get(i).onDragFinished(x, y);
+ }
+ }
+
+ public void addOnDragDropListener(OnDragDropListener listener) {
+ if (!mOnDragDropListeners.contains(listener)) {
+ mOnDragDropListeners.add(listener);
+ }
+ }
+
+ public void removeOnDragDropListener(OnDragDropListener listener) {
+ if (mOnDragDropListeners.contains(listener)) {
+ mOnDragDropListeners.remove(listener);
+ }
+ }
+
+} \ No newline at end of file
diff --git a/src/com/android/dialer/list/OnDragDropListener.java b/src/com/android/dialer/list/OnDragDropListener.java
new file mode 100644
index 000000000..7f6d1791c
--- /dev/null
+++ b/src/com/android/dialer/list/OnDragDropListener.java
@@ -0,0 +1,41 @@
+package com.android.dialer.list;
+
+
+/**
+ * Classes that want to receive callbacks in response to drag events should implement this
+ * interface.
+ */
+public interface OnDragDropListener {
+ /**
+ * Called when a drag is started.
+ * @param itemIndex Index of the contact on which the drag was triggered
+ * @param x X-coordinate of the drag event
+ * @param y Y-coordinate of the drag event
+ * @param view The contact tile which the drag was started on
+ */
+ public void onDragStarted(int itemIndex, int x, int y, PhoneFavoriteTileView view);
+
+ /**
+ * Called when a drag is in progress and the user moves the dragged contact to a
+ * location.
+ * @param itemIndex Index of the contact in the ListView which is currently being displaced
+ * by the dragged contact
+ * @param x X-coordinate of the drag event
+ * @param y Y-coordinate of the drag event
+ */
+ public void onDragHovered(int itemIndex, int x, int y);
+
+ /**
+ * Called when a drag is completed (whether by dropping it somewhere or simply by dragging
+ * the contact off the screen)
+ * @param x X-coordinate of the drag event
+ * @param y Y-coordinate of the drag event
+ */
+ public void onDragFinished(int x, int y);
+
+ /**
+ * Called when a contact has been dropped on the remove view, indicating that the user
+ * wants to remove this contact.
+ */
+ public void onDroppedOnRemove();
+} \ No newline at end of file
diff --git a/src/com/android/dialer/list/PhoneFavoriteFragment.java b/src/com/android/dialer/list/PhoneFavoriteFragment.java
index 860f9dc2a..79dbe8c49 100644
--- a/src/com/android/dialer/list/PhoneFavoriteFragment.java
+++ b/src/com/android/dialer/list/PhoneFavoriteFragment.java
@@ -107,6 +107,10 @@ public class PhoneFavoriteFragment extends Fragment implements OnItemClickListen
public void onCallNumberDirectly(String phoneNumber);
}
+ public interface HostInterface {
+ public void setDragDropController(DragDropController controller);
+ }
+
private class MissedCallLogLoaderListener implements LoaderManager.LoaderCallbacks<Cursor> {
@Override
@@ -279,7 +283,7 @@ public class PhoneFavoriteFragment extends Fragment implements OnItemClickListen
mListView.setVerticalScrollbarPosition(View.SCROLLBAR_POSITION_RIGHT);
mListView.setScrollBarStyle(ListView.SCROLLBARS_OUTSIDE_OVERLAY);
mListView.setOnItemSwipeListener(mContactTileAdapter);
- mListView.setOnDragDropListener(mContactTileAdapter);
+ mListView.getDragDropController().addOnDragDropListener(mContactTileAdapter);
final ImageView dragShadowOverlay =
(ImageView) mParentView.findViewById(R.id.contact_tile_drag_shadow_overlay);
@@ -347,6 +351,15 @@ public class PhoneFavoriteFragment extends Fragment implements OnItemClickListen
+ " must implement OnShowAllContactsListener");
}
+ try {
+ OnDragDropListener listener = (OnDragDropListener) activity;
+ mListView.getDragDropController().addOnDragDropListener(listener);
+ ((HostInterface) activity).setDragDropController(mListView.getDragDropController());
+ } catch (ClassCastException e) {
+ throw new ClassCastException(activity.toString()
+ + " must implement OnDragDropListener and HostInterface");
+ }
+
// Use initLoader() instead of restartLoader() to refraining unnecessary reload.
// This method call implicitly assures ContactTileLoaderListener's onLoadFinished() will
// be called, on which we'll check if "all" contacts should be reloaded again or not.
diff --git a/src/com/android/dialer/list/PhoneFavoriteListView.java b/src/com/android/dialer/list/PhoneFavoriteListView.java
index 99979dd53..adda3cfd0 100644
--- a/src/com/android/dialer/list/PhoneFavoriteListView.java
+++ b/src/com/android/dialer/list/PhoneFavoriteListView.java
@@ -29,7 +29,6 @@ import android.view.DragEvent;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewConfiguration;
-import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.ListView;
@@ -44,7 +43,8 @@ import com.android.dialer.list.SwipeHelper.SwipeHelperCallback;
* - Swiping, which is borrowed from packages/apps/UnifiedEmail (com.android.mail.ui.Swipeable)
* - Drag and drop
*/
-public class PhoneFavoriteListView extends ListView implements SwipeHelperCallback {
+public class PhoneFavoriteListView extends ListView implements SwipeHelperCallback,
+ OnDragDropListener {
public static final String LOG_TAG = PhoneFavoriteListView.class.getSimpleName();
@@ -52,7 +52,6 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
private boolean mEnableSwipe = true;
private OnItemGestureListener mOnItemGestureListener;
- private OnDragDropListener mOnDragDropListener;
private float mDensityScale;
private float mTouchSlop;
@@ -81,6 +80,8 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
private int mDragShadowLeft;
private int mDragShadowTop;
+ private DragDropController mDragDropController = new DragDropController();
+
private final float DRAG_SHADOW_ALPHA = 0.7f;
/**
@@ -130,6 +131,7 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
mSwipeHelper = new SwipeHelper(context, SwipeHelper.X, this,
mDensityScale, mTouchSlop);
setItemsCanFocus(true);
+ mDragDropController.addOnDragDropListener(this);
}
@Override
@@ -156,10 +158,10 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
mOnItemGestureListener = listener;
}
- public void setOnDragDropListener(OnDragDropListener listener) {
- mOnDragDropListener = listener;
- }
-
+ /**
+ * TODO: This is all swipe to remove code (nothing to do with drag to remove). This should
+ * be cleaned up and removed once drag to remove becomes the only way to remove contacts.
+ */
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
if (ev.getAction() == MotionEvent.ACTION_DOWN) {
@@ -232,6 +234,10 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
requestDisallowInterceptTouchEvent(true);
}
+ /**
+ * End of swipe-to-remove code
+ */
+
@Override
public boolean dispatchDragEvent(DragEvent event) {
final int action = event.getAction();
@@ -239,13 +245,34 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
final int eY = (int) event.getY();
switch (action) {
case DragEvent.ACTION_DRAG_STARTED:
- if (!handleDragStarted(mTouchDownForDragStartX, mTouchDownForDragStartY)) {
+ final int[] coordinates = new int[2];
+ getLocationOnScreen(coordinates);
+ // Calculate the X and Y coordinates of the drag event relative to the view
+ final int viewX = eX - coordinates[0];
+ final int viewY = eY - coordinates[1];
+ final View child = getViewAtPosition(viewX, viewY);
+
+ if (!(child instanceof ContactTileRow)) {
+ // Bail early.
+ return false;
+ }
+
+ final ContactTileRow tile = (ContactTileRow) child;
+
+ // Disable drag and drop if there is a contact that has been swiped and is currently
+ // in the pending remove state
+ if (tile.getTileAdapter().hasPotentialRemoveEntryIndex()) {
+ return false;
+ }
+
+ if (!mDragDropController.handleDragStarted(viewX, viewY, tile)) {
return false;
- };
+ }
break;
case DragEvent.ACTION_DRAG_LOCATION:
mLastDragY = eY;
- handleDragHovered(eX, eY);
+ final View view = getViewAtPosition(eX, eY);
+ mDragDropController.handleDragHovered(eX, eY, view);
// Kick off {@link #mScrollHandler} if it's not started yet.
if (!mIsDragScrollerRunning &&
// And if the distance traveled while dragging exceeds the touch slop
@@ -268,13 +295,13 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
mIsDragScrollerRunning = false;
// Either a successful drop or it's ended with out drop.
if (action == DragEvent.ACTION_DROP || action == DragEvent.ACTION_DRAG_ENDED) {
- handleDragFinished(eX, eY);
+ mDragDropController.handleDragFinished(eX, eY, false);
}
break;
default:
break;
}
- // This ListView will consumer the drag events on behalf of its children.
+ // This ListView will consume the drag events on behalf of its children.
return true;
}
@@ -303,69 +330,48 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
}
}
- /**
- * @return True if the drag is started.
- */
- private boolean handleDragStarted(int x, int y) {
- final View child = getViewAtPosition(x, y);
- if (!(child instanceof ContactTileRow)) {
- // Bail early.
- return false;
- }
-
- final ContactTileRow tile = (ContactTileRow) child;
+ public DragDropController getDragDropController() {
+ return mDragDropController;
+ }
- if (tile.getTileAdapter().hasPotentialRemoveEntryIndex()) {
- return false;
+ @Override
+ public void onDragStarted(int itemIndex, int x, int y, PhoneFavoriteTileView tileView) {
+ if (mDragShadowOverlay == null) {
+ return;
}
- final int itemIndex = tile.getItemIndex(x, y);
- if (itemIndex != -1 && mOnDragDropListener != null) {
- final PhoneFavoriteTileView tileView =
- (PhoneFavoriteTileView) tile.getViewAtPosition(x, y);
- if (mDragShadowOverlay == null) {
- return false;
- }
-
- mDragShadowOverlay.clearAnimation();
- mDragShadowBitmap = createDraggedChildBitmap(tileView);
- if (mDragShadowBitmap == null) {
- return false;
- }
-
- if (tileView instanceof PhoneFavoriteRegularRowView) {
- mDragShadowLeft = tile.getLeft();
- mDragShadowTop = tile.getTop();
- } else {
- // Square tile is relative to the contact tile,
- // and contact tile is relative to this list view.
- mDragShadowLeft = tileView.getLeft() + tileView.getParentRow().getLeft();
- mDragShadowTop = tileView.getTop() + tileView.getParentRow().getTop();
- }
-
- mDragShadowOverlay.setImageBitmap(mDragShadowBitmap);
- mDragShadowOverlay.setVisibility(VISIBLE);
- mDragShadowOverlay.setAlpha(DRAG_SHADOW_ALPHA);
-
- mDragShadowOverlay.setX(mDragShadowLeft);
- mDragShadowOverlay.setY(mDragShadowTop);
+ mDragShadowOverlay.clearAnimation();
+ mDragShadowBitmap = createDraggedChildBitmap(tileView);
+ if (mDragShadowBitmap == null) {
+ return;
+ }
- // x and y passed in are the coordinates of where the user has touched down, calculate
- // the offset to the top left coordinate of the dragged child. This will be used for
- // drawing the drag shadow.
- mTouchOffsetToChildLeft = x - mDragShadowLeft;
- mTouchOffsetToChildTop = y - mDragShadowTop;
+ if (tileView instanceof PhoneFavoriteRegularRowView) {
+ mDragShadowLeft = tileView.getParentRow().getLeft();
+ mDragShadowTop = tileView.getParentRow().getTop();
+ } else {
+ // Square tile is relative to the contact tile,
+ // and contact tile is relative to this list view.
+ mDragShadowLeft = tileView.getLeft() + tileView.getParentRow().getLeft();
+ mDragShadowTop = tileView.getTop() + tileView.getParentRow().getTop();
+ }
- // invalidate to trigger a redraw of the drag shadow.
- invalidate();
+ mDragShadowOverlay.setImageBitmap(mDragShadowBitmap);
+ mDragShadowOverlay.setVisibility(VISIBLE);
+ mDragShadowOverlay.setAlpha(DRAG_SHADOW_ALPHA);
- mOnDragDropListener.onDragStarted(itemIndex);
- }
+ mDragShadowOverlay.setX(mDragShadowLeft);
+ mDragShadowOverlay.setY(mDragShadowTop);
- return true;
+ // x and y passed in are the coordinates of where the user has touched down,
+ // calculate the offset to the top left coordinate of the dragged child. This
+ // will be used for drawing the drag shadow.
+ mTouchOffsetToChildLeft = x - mDragShadowLeft;
+ mTouchOffsetToChildTop = y - mDragShadowTop;
}
- private void handleDragHovered(int x, int y) {
+ @Override
+ public void onDragHovered(int itemIndex, int x, int y) {
// Update the drag shadow location.
mDragShadowLeft = x - mTouchOffsetToChildLeft;
mDragShadowTop = y - mTouchOffsetToChildTop;
@@ -374,21 +380,10 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
mDragShadowOverlay.setX(mDragShadowLeft);
mDragShadowOverlay.setY(mDragShadowTop);
}
-
- final View child = getViewAtPosition(x, y);
- if (!(child instanceof ContactTileRow)) {
- // Bail early.
- return;
- }
-
- final ContactTileRow tile = (ContactTileRow) child;
- final int itemIndex = tile.getItemIndex(x, y);
- if (itemIndex != -1 && mOnDragDropListener != null) {
- mOnDragDropListener.onDragHovered(itemIndex);
- }
}
- private void handleDragFinished(int x, int y) {
+ @Override
+ public void onDragFinished(int x, int y) {
// Update the drag shadow location.
mDragShadowLeft = x - mTouchOffsetToChildLeft;
mDragShadowTop = y - mTouchOffsetToChildTop;
@@ -400,12 +395,11 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
.setListener(mDragShadowOverAnimatorListener)
.start();
}
-
- if (mOnDragDropListener != null) {
- mOnDragDropListener.onDragFinished();
- }
}
+ @Override
+ public void onDroppedOnRemove() {}
+
private Bitmap createDraggedChildBitmap(View view) {
view.setDrawingCacheEnabled(true);
final Bitmap cache = view.getDrawingCache();
@@ -425,10 +419,4 @@ public class PhoneFavoriteListView extends ListView implements SwipeHelperCallba
return bitmap;
}
-
- public interface OnDragDropListener {
- public void onDragStarted(int itemIndex);
- public void onDragHovered(int itemIndex);
- public void onDragFinished();
- }
}
diff --git a/src/com/android/dialer/list/PhoneFavoritesTileAdapter.java b/src/com/android/dialer/list/PhoneFavoritesTileAdapter.java
index dff68b2be..45cc5a371 100644
--- a/src/com/android/dialer/list/PhoneFavoritesTileAdapter.java
+++ b/src/com/android/dialer/list/PhoneFavoritesTileAdapter.java
@@ -59,7 +59,7 @@ import java.util.PriorityQueue;
*
*/
public class PhoneFavoritesTileAdapter extends BaseAdapter implements
- SwipeHelper.OnItemGestureListener, PhoneFavoriteListView.OnDragDropListener {
+ SwipeHelper.OnItemGestureListener, OnDragDropListener {
private static final String TAG = PhoneFavoritesTileAdapter.class.getSimpleName();
private static final boolean DEBUG = false;
@@ -1204,24 +1204,38 @@ public class PhoneFavoritesTileAdapter extends BaseAdapter implements
}
@Override
- public void onDragStarted(int itemIndex) {
+ public void onDragStarted(int itemIndex, int x, int y, PhoneFavoriteTileView view) {
setInDragging(true);
popContactEntry(itemIndex);
}
@Override
- public void onDragHovered(int itemIndex) {
+ public void onDragHovered(int itemIndex, int x, int y) {
if (mInDragging &&
mDragEnteredEntryIndex != itemIndex &&
isIndexInBound(itemIndex) &&
- itemIndex < PIN_LIMIT) {
+ itemIndex < PIN_LIMIT &&
+ itemIndex >= 0) {
markDropArea(itemIndex);
}
}
@Override
- public void onDragFinished() {
+ public void onDragFinished(int x, int y) {
setInDragging(false);
- handleDrop();
+ // A contact has been dragged to the RemoveView in order to be unstarred, so simply wait
+ // for the new contact cursor which will cause the UI to be refreshed without the unstarred
+ // contact.
+ if (!mAwaitingRemove) {
+ handleDrop();
+ }
+ }
+
+ @Override
+ public void onDroppedOnRemove() {
+ if (mDraggedEntry != null) {
+ unstarAndUnpinContact(mDraggedEntry.lookupKey);
+ mAwaitingRemove = true;
+ }
}
}
diff --git a/src/com/android/dialer/list/RemoveView.java b/src/com/android/dialer/list/RemoveView.java
new file mode 100644
index 000000000..16942fe96
--- /dev/null
+++ b/src/com/android/dialer/list/RemoveView.java
@@ -0,0 +1,90 @@
+package com.android.dialer.list;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.drawable.Drawable;
+import android.util.AttributeSet;
+import android.view.DragEvent;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import com.android.dialer.R;
+
+public class RemoveView extends LinearLayout {
+
+ DragDropController mDragDropController;
+ TextView mRemoveText;
+ ImageView mRemoveIcon;
+ int mUnhighlightedColor;
+ int mHighlightedColor;
+ Drawable mRemoveDrawable;
+ Drawable mRemoveHighlightedDrawable;
+
+ public RemoveView(Context context) {
+ super(context);
+ }
+
+ public RemoveView(Context context, AttributeSet attrs) {
+ this(context, attrs, -1);
+ }
+
+ public RemoveView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ }
+
+ @Override
+ protected void onFinishInflate() {
+ mRemoveText = (TextView) findViewById(R.id.remove_view_text);
+ mRemoveIcon = (ImageView) findViewById(R.id.remove_view_icon);
+ final Resources r = getResources();
+ mUnhighlightedColor = r.getColor(R.color.remove_text_color);
+ mHighlightedColor = r.getColor(R.color.remove_highlighted_text_color);
+ mRemoveDrawable = r.getDrawable(R.drawable.ic_remove);
+ mRemoveHighlightedDrawable = r.getDrawable(R.drawable.ic_remove_highlight);
+ }
+
+ public void setDragDropController(DragDropController controller) {
+ mDragDropController = controller;
+ }
+
+ @Override
+ public boolean dispatchDragEvent(DragEvent event) {
+ final int action = event.getAction();
+ switch (action) {
+ case DragEvent.ACTION_DRAG_ENTERED:
+ setAppearanceHighlighted();
+ break;
+ case DragEvent.ACTION_DRAG_EXITED:
+ setAppearanceNormal();
+ break;
+ case DragEvent.ACTION_DRAG_LOCATION:
+ if (mDragDropController != null) {
+ mDragDropController.handleDragHovered((int) event.getX(),
+ // the true y-coordinate of the event with respect to the listview is
+ // offset by the height of the remove view
+ (int) event.getY() - getHeight(), null);
+ }
+ break;
+ case DragEvent.ACTION_DROP:
+ if (mDragDropController != null) {
+ mDragDropController.handleDragFinished((int) event.getX(), (int) event.getY(), true);
+ }
+ setAppearanceNormal();
+ break;
+ }
+ return true;
+ }
+
+ private void setAppearanceNormal() {
+ mRemoveText.setTextColor(mUnhighlightedColor);
+ mRemoveIcon.setImageDrawable(mRemoveDrawable);
+ invalidate();
+ }
+
+ private void setAppearanceHighlighted() {
+ mRemoveText.setTextColor(mHighlightedColor);
+ mRemoveIcon.setImageDrawable(mRemoveHighlightedDrawable);
+ invalidate();
+ }
+}