1 /* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.launcher3; 18 19 import android.animation.TimeInterpolator; 20 import android.content.Context; 21 import android.graphics.PointF; 22 import android.util.AttributeSet; 23 import android.view.View; 24 import android.view.animation.AnimationUtils; 25 26 import com.android.launcher3.util.FlingAnimation; 27 import com.android.launcher3.util.Thunk; 28 29 public class DeleteDropTarget extends ButtonDropTarget { 30 DeleteDropTarget(Context context, AttributeSet attrs)31 public DeleteDropTarget(Context context, AttributeSet attrs) { 32 this(context, attrs, 0); 33 } 34 DeleteDropTarget(Context context, AttributeSet attrs, int defStyle)35 public DeleteDropTarget(Context context, AttributeSet attrs, int defStyle) { 36 super(context, attrs, defStyle); 37 } 38 39 @Override onFinishInflate()40 protected void onFinishInflate() { 41 super.onFinishInflate(); 42 // Get the hover color 43 mHoverColor = getResources().getColor(R.color.delete_target_hover_tint); 44 45 setDrawable(R.drawable.ic_remove_launcher); 46 } 47 supportsDrop(Object info)48 public static boolean supportsDrop(Object info) { 49 return (info instanceof ShortcutInfo) 50 || (info instanceof LauncherAppWidgetInfo) 51 || (info instanceof FolderInfo); 52 } 53 54 @Override supportsDrop(DragSource source, Object info)55 protected boolean supportsDrop(DragSource source, Object info) { 56 return source.supportsDeleteDropTarget() && supportsDrop(info); 57 } 58 59 @Override completeDrop(DragObject d)60 @Thunk void completeDrop(DragObject d) { 61 ItemInfo item = (ItemInfo) d.dragInfo; 62 if ((d.dragSource instanceof Workspace) || (d.dragSource instanceof Folder)) { 63 removeWorkspaceOrFolderItem(mLauncher, item, null); 64 } 65 } 66 67 /** 68 * Removes the item from the workspace. If the view is not null, it also removes the view. 69 */ removeWorkspaceOrFolderItem(Launcher launcher, ItemInfo item, View view)70 public static void removeWorkspaceOrFolderItem(Launcher launcher, ItemInfo item, View view) { 71 // Remove the item from launcher and the db, we can ignore the containerInfo in this call 72 // because we already remove the drag view from the folder (if the drag originated from 73 // a folder) in Folder.beginDrag() 74 launcher.removeItem(view, item, true /* deleteFromDb */); 75 launcher.getWorkspace().stripEmptyScreens(); 76 launcher.getDragLayer().announceForAccessibility(launcher.getString(R.string.item_removed)); 77 } 78 79 @Override onFlingToDelete(final DragObject d, PointF vel)80 public void onFlingToDelete(final DragObject d, PointF vel) { 81 // Don't highlight the icon as it's animating 82 d.dragView.setColor(0); 83 d.dragView.updateInitialScaleToCurrentScale(); 84 85 final DragLayer dragLayer = mLauncher.getDragLayer(); 86 FlingAnimation fling = new FlingAnimation(d, vel, 87 getIconRect(d.dragView.getMeasuredWidth(), d.dragView.getMeasuredHeight(), 88 mDrawable.getIntrinsicWidth(), mDrawable.getIntrinsicHeight()), 89 dragLayer); 90 91 final int duration = fling.getDuration(); 92 final long startTime = AnimationUtils.currentAnimationTimeMillis(); 93 94 // NOTE: Because it takes time for the first frame of animation to actually be 95 // called and we expect the animation to be a continuation of the fling, we have 96 // to account for the time that has elapsed since the fling finished. And since 97 // we don't have a startDelay, we will always get call to update when we call 98 // start() (which we want to ignore). 99 final TimeInterpolator tInterpolator = new TimeInterpolator() { 100 private int mCount = -1; 101 private float mOffset = 0f; 102 103 @Override 104 public float getInterpolation(float t) { 105 if (mCount < 0) { 106 mCount++; 107 } else if (mCount == 0) { 108 mOffset = Math.min(0.5f, (float) (AnimationUtils.currentAnimationTimeMillis() - 109 startTime) / duration); 110 mCount++; 111 } 112 return Math.min(1f, mOffset + t); 113 } 114 }; 115 116 Runnable onAnimationEndRunnable = new Runnable() { 117 @Override 118 public void run() { 119 mLauncher.exitSpringLoadedDragMode(); 120 completeDrop(d); 121 mLauncher.getDragController().onDeferredEndFling(d); 122 } 123 }; 124 125 dragLayer.animateView(d.dragView, fling, duration, tInterpolator, onAnimationEndRunnable, 126 DragLayer.ANIMATION_END_DISAPPEAR, null); 127 } 128 } 129