diff options
Diffstat (limited to 'go')
9 files changed, 150 insertions, 26 deletions
diff --git a/go/quickstep/res/layout/task_item_view.xml b/go/quickstep/res/layout/task_item_view.xml index 90940c495..ee67d49fc 100644 --- a/go/quickstep/res/layout/task_item_view.xml +++ b/go/quickstep/res/layout/task_item_view.xml @@ -19,12 +19,24 @@ android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal"> - <ImageView + <FrameLayout android:id="@+id/task_icon_and_thumbnail" - android:layout_width="@dimen/task_thumbnail_icon_size" - android:layout_height="@dimen/task_thumbnail_icon_size" + android:layout_width="@dimen/task_item_height" + android:layout_height="@dimen/task_item_height" android:layout_gravity="center_vertical" - android:layout_marginHorizontal="8dp"/> + android:layout_marginHorizontal="8dp" + android:layout_marginVertical="@dimen/task_item_half_vert_margin"> + <ImageView + android:id="@+id/task_thumbnail" + android:layout_width="wrap_content" + android:layout_height="match_parent" + android:layout_gravity="top|start"/> + <ImageView + android:id="@+id/task_icon" + android:layout_width="@dimen/task_icon_size" + android:layout_height="@dimen/task_icon_size" + android:layout_gravity="bottom|end"/> + </FrameLayout> <TextView android:id="@+id/task_label" android:layout_width="wrap_content" diff --git a/go/quickstep/res/values/dimens.xml b/go/quickstep/res/values/dimens.xml new file mode 100644 index 000000000..28cc1ebe6 --- /dev/null +++ b/go/quickstep/res/values/dimens.xml @@ -0,0 +1,21 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + Copyright (C) 2019 The Android Open Source Project + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--> +<resources> + <dimen name="task_item_height">60dp</dimen> + <dimen name="task_item_half_vert_margin">8dp</dimen> + <dimen name="task_icon_size">36dp</dimen> +</resources>
\ No newline at end of file diff --git a/go/quickstep/src/com/android/quickstep/TaskAdapter.java b/go/quickstep/src/com/android/quickstep/TaskAdapter.java index 99446d07d..4f3d1e4a0 100644 --- a/go/quickstep/src/com/android/quickstep/TaskAdapter.java +++ b/go/quickstep/src/com/android/quickstep/TaskAdapter.java @@ -25,7 +25,8 @@ import com.android.launcher3.R; import com.android.quickstep.views.TaskItemView; import com.android.systemui.shared.recents.model.Task; -import java.util.ArrayList; +import java.util.List; + /** * Recycler view adapter that dynamically inflates and binds {@link TaskHolder} instances with the * appropriate {@link Task} from the recents task list. @@ -56,7 +57,7 @@ public final class TaskAdapter extends Adapter<TaskHolder> { @Override public void onBindViewHolder(TaskHolder holder, int position) { - ArrayList<Task> tasks = mLoader.getCurrentTaskList(); + List<Task> tasks = mLoader.getCurrentTaskList(); if (position >= tasks.size()) { // Task list has updated. return; diff --git a/go/quickstep/src/com/android/quickstep/TaskHolder.java b/go/quickstep/src/com/android/quickstep/TaskHolder.java index 67e8ece22..8d5e4d55f 100644 --- a/go/quickstep/src/com/android/quickstep/TaskHolder.java +++ b/go/quickstep/src/com/android/quickstep/TaskHolder.java @@ -45,6 +45,7 @@ final class TaskHolder extends ViewHolder { mTask = task; mTaskItemView.setLabel(task.titleDescription); mTaskItemView.setIcon(task.icon); + mTaskItemView.setThumbnail(task.thumbnail.thumbnail); } /** diff --git a/go/quickstep/src/com/android/quickstep/TaskInputController.java b/go/quickstep/src/com/android/quickstep/TaskInputController.java index 66c449649..d97ac8da9 100644 --- a/go/quickstep/src/com/android/quickstep/TaskInputController.java +++ b/go/quickstep/src/com/android/quickstep/TaskInputController.java @@ -15,6 +15,7 @@ */ package com.android.quickstep; +import com.android.systemui.shared.recents.model.Task; import com.android.systemui.shared.system.ActivityManagerWrapper; /** @@ -22,9 +23,11 @@ import com.android.systemui.shared.system.ActivityManagerWrapper; */ public final class TaskInputController { - TaskAdapter mAdapter; + private final TaskListLoader mLoader; + private final TaskAdapter mAdapter; - public TaskInputController(TaskAdapter adapter) { + public TaskInputController(TaskListLoader loader,TaskAdapter adapter) { + mLoader = loader; mAdapter = adapter; } @@ -39,7 +42,14 @@ public final class TaskInputController { null /* options */, null /* resultCallback */, null /* resultCallbackHandler */); } - // TODO: Implement swipe to delete and notify adapter that data has updated + public void onTaskSwiped(TaskHolder viewHolder) { + int position = viewHolder.getAdapterPosition(); + Task task = viewHolder.getTask(); + ActivityManagerWrapper.getInstance().removeTask(task.key.id); + mLoader.removeTask(task); + mAdapter.notifyItemRemoved(position); + } // TODO: Implement "Clear all" and notify adapter that data has updated + } diff --git a/go/quickstep/src/com/android/quickstep/TaskListLoader.java b/go/quickstep/src/com/android/quickstep/TaskListLoader.java index c798cef1e..e6d1a22df 100644 --- a/go/quickstep/src/com/android/quickstep/TaskListLoader.java +++ b/go/quickstep/src/com/android/quickstep/TaskListLoader.java @@ -24,6 +24,7 @@ import com.android.systemui.shared.recents.model.Task; import java.util.ArrayList; import java.util.Collections; +import java.util.List; import java.util.concurrent.atomic.AtomicInteger; import java.util.function.Consumer; @@ -45,13 +46,13 @@ public final class TaskListLoader { /** * Returns the current task list as of the last completed load (see - * {@link #loadTaskList}). This list of tasks is guaranteed to always have all its task - * content loaded. + * {@link #loadTaskList}) as a read-only list. This list of tasks is guaranteed to always have + * all its task content loaded. * * @return the current list of tasks w/ all content loaded */ - public ArrayList<Task> getCurrentTaskList() { - return mTaskList; + public List<Task> getCurrentTaskList() { + return Collections.unmodifiableList(mTaskList); } /** @@ -85,6 +86,13 @@ public final class TaskListLoader { } /** + * Removes the task from the current task list. + */ + void removeTask(Task task) { + mTaskList.remove(task); + } + + /** * Loads task content for a list of tasks, including the label, icon, and thumbnail. For content * that isn't cached, load the content asynchronously in the background. * diff --git a/go/quickstep/src/com/android/quickstep/TaskSwipeCallback.java b/go/quickstep/src/com/android/quickstep/TaskSwipeCallback.java new file mode 100644 index 000000000..2a539172b --- /dev/null +++ b/go/quickstep/src/com/android/quickstep/TaskSwipeCallback.java @@ -0,0 +1,48 @@ +/* + * Copyright (C) 2019 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.quickstep; + +import static androidx.recyclerview.widget.ItemTouchHelper.RIGHT; + +import androidx.recyclerview.widget.ItemTouchHelper; +import androidx.recyclerview.widget.RecyclerView; +import androidx.recyclerview.widget.RecyclerView.ViewHolder; + +/** + * Callback for swipe input on {@link TaskHolder} views in the recents view. + */ +public final class TaskSwipeCallback extends ItemTouchHelper.SimpleCallback { + + private final TaskInputController mTaskInputController; + + public TaskSwipeCallback(TaskInputController inputController) { + super(0 /* dragDirs */, RIGHT); + mTaskInputController = inputController; + } + + @Override + public boolean onMove(RecyclerView recyclerView, ViewHolder viewHolder, + ViewHolder target) { + return false; + } + + @Override + public void onSwiped(ViewHolder viewHolder, int direction) { + if (direction == RIGHT) { + mTaskInputController.onTaskSwiped((TaskHolder) viewHolder); + } + } +} diff --git a/go/quickstep/src/com/android/quickstep/views/IconRecentsView.java b/go/quickstep/src/com/android/quickstep/views/IconRecentsView.java index e8a915f64..b7740eb50 100644 --- a/go/quickstep/src/com/android/quickstep/views/IconRecentsView.java +++ b/go/quickstep/src/com/android/quickstep/views/IconRecentsView.java @@ -23,6 +23,7 @@ import android.util.FloatProperty; import android.view.ViewDebug; import android.widget.FrameLayout; +import androidx.recyclerview.widget.ItemTouchHelper; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; @@ -30,6 +31,7 @@ import com.android.launcher3.R; import com.android.quickstep.TaskAdapter; import com.android.quickstep.TaskInputController; import com.android.quickstep.TaskListLoader; +import com.android.quickstep.TaskSwipeCallback; /** * Root view for the icon recents view. Acts as the main interface to the rest of the Launcher code @@ -76,29 +78,35 @@ public final class IconRecentsView extends FrameLayout { @ViewDebug.ExportedProperty(category = "launcher") private final Context mContext; + private final TaskListLoader mTaskLoader; + private final TaskAdapter mTaskAdapter; + private final TaskInputController mTaskInputController; private float mTranslationYFactor; - private TaskAdapter mTaskAdapter; private RecyclerView mTaskRecyclerView; - private TaskInputController mTaskInputController; - private TaskListLoader mTaskLoader; + public IconRecentsView(Context context, AttributeSet attrs) { super(context, attrs); mContext = context; + mTaskLoader = new TaskListLoader(mContext); + mTaskAdapter = new TaskAdapter(mTaskLoader); + mTaskInputController = new TaskInputController(mTaskLoader, mTaskAdapter); + mTaskAdapter.setInputController(mTaskInputController); } @Override protected void onFinishInflate() { super.onFinishInflate(); - mTaskLoader = new TaskListLoader(mContext); - mTaskAdapter = new TaskAdapter(mTaskLoader); - mTaskInputController = new TaskInputController(mTaskAdapter); - mTaskAdapter.setInputController(mTaskInputController); - mTaskRecyclerView = findViewById(R.id.recent_task_recycler_view); - mTaskRecyclerView.setAdapter(mTaskAdapter); - mTaskRecyclerView.setLayoutManager( - new LinearLayoutManager(mContext, VERTICAL, true /* reverseLayout */)); + if (mTaskRecyclerView == null) { + mTaskRecyclerView = findViewById(R.id.recent_task_recycler_view); + mTaskRecyclerView.setAdapter(mTaskAdapter); + mTaskRecyclerView.setLayoutManager( + new LinearLayoutManager(mContext, VERTICAL, true /* reverseLayout */)); + ItemTouchHelper helper = new ItemTouchHelper( + new TaskSwipeCallback(mTaskInputController)); + helper.attachToRecyclerView(mTaskRecyclerView); + } } /** diff --git a/go/quickstep/src/com/android/quickstep/views/TaskItemView.java b/go/quickstep/src/com/android/quickstep/views/TaskItemView.java index ce3947d24..3818965b7 100644 --- a/go/quickstep/src/com/android/quickstep/views/TaskItemView.java +++ b/go/quickstep/src/com/android/quickstep/views/TaskItemView.java @@ -16,6 +16,7 @@ package com.android.quickstep.views; import android.content.Context; +import android.graphics.Bitmap; import android.graphics.drawable.Drawable; import android.util.AttributeSet; import android.widget.ImageView; @@ -31,6 +32,7 @@ public final class TaskItemView extends LinearLayout { private TextView mLabelView; private ImageView mIconView; + private ImageView mThumbnailView; public TaskItemView(Context context, AttributeSet attrs) { super(context, attrs); @@ -40,7 +42,8 @@ public final class TaskItemView extends LinearLayout { protected void onFinishInflate() { super.onFinishInflate(); mLabelView = findViewById(R.id.task_label); - mIconView = findViewById(R.id.task_icon_and_thumbnail); + mThumbnailView = findViewById(R.id.task_thumbnail); + mIconView = findViewById(R.id.task_icon); } /** @@ -58,7 +61,19 @@ public final class TaskItemView extends LinearLayout { * @param icon task icon */ public void setIcon(Drawable icon) { + // TODO: Scale the icon up based off the padding on the side + // The icon proper is actually smaller than the drawable and has "padding" on the side for + // the purpose of drawing the shadow, allowing the icon to pop up, so we need to scale the + // view if we want the icon to be flush with the bottom of the thumbnail. mIconView.setImageDrawable(icon); - // TODO: Add in combination drawable for icon + thumbnail + } + + /** + * Set the task thumbnail for the task. + * + * @param thumbnail task thumbnail for the task + */ + public void setThumbnail(Bitmap thumbnail) { + mThumbnailView.setImageBitmap(thumbnail); } } |