Render user's actual workspace in ThemePicker preview (Part 2)

With this change, we can also render folders in preview. It's built on top of part 1.

Test: Go to grid options, choose a different grid option, and see user's workspace rendered in the preview
Bug: 144052839
Change-Id: Iaf6d8af6b909ece4147ea250d95dec3d2c0019d3
This commit is contained in:
Tracy Zhou 2019-12-09 13:42:57 -08:00
parent 290f2cb028
commit 4d7b244f3f
6 changed files with 60 additions and 35 deletions

View File

@ -47,7 +47,7 @@ public class PredictedAppIcon extends DoubleShadowBubbleTextView {
private static final float RING_EFFECT_RATIO = 0.11f;
private DeviceProfile mDeviceProfile;
private final DeviceProfile mDeviceProfile;
private final Paint mIconRingPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
private boolean mIsPinned = false;
private int mNormalizedIconRadius;
@ -65,7 +65,7 @@ public class PredictedAppIcon extends DoubleShadowBubbleTextView {
mDeviceProfile = Launcher.getLauncher(context).getDeviceProfile();
mNormalizedIconRadius = IconNormalizer.getNormalizedCircleSize(getIconSize()) / 2;
setOnClickListener(ItemClickHandler.INSTANCE);
setOnFocusChangeListener(Launcher.getLauncher(context).mFocusHandler);
setOnFocusChangeListener(Launcher.getLauncher(context).getFocusHandler());
}
@Override

View File

@ -307,7 +307,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns,
// Request id for any pending activity result
protected int mPendingActivityRequestCode = -1;
public ViewGroupFocusHelper mFocusHandler;
private ViewGroupFocusHelper mFocusHandler;
private RotationHelper mRotationHelper;
@ -617,6 +617,10 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns,
return mRotationHelper;
}
public ViewGroupFocusHelper getFocusHandler() {
return mFocusHandler;
}
public LauncherStateManager getStateManager() {
return mStateManager;
}
@ -1740,7 +1744,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns,
getModelWriter().addItemToDatabase(folderInfo, container, screenId, cellX, cellY);
// Create the view
FolderIcon newFolder = FolderIcon.fromXml(R.layout.folder_icon, this, layout, folderInfo);
FolderIcon newFolder = FolderIcon.inflateFolderAndIcon(R.layout.folder_icon, this, layout, folderInfo);
mWorkspace.addInScreen(newFolder, folderInfo);
// Force measure the new folder icon
CellLayout parent = mWorkspace.getParentCellLayoutForView(newFolder);
@ -2101,7 +2105,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns,
break;
}
case LauncherSettings.Favorites.ITEM_TYPE_FOLDER: {
view = FolderIcon.fromXml(R.layout.folder_icon, this,
view = FolderIcon.inflateFolderAndIcon(R.layout.folder_icon, this,
(ViewGroup) workspace.getChildAt(workspace.getCurrentPage()),
(FolderInfo) item);
break;

View File

@ -83,7 +83,6 @@ import com.android.launcher3.logging.UserEventDispatcher;
import com.android.launcher3.pageindicators.WorkspacePageIndicator;
import com.android.launcher3.popup.PopupContainerWithArrow;
import com.android.launcher3.shortcuts.ShortcutDragPreviewProvider;
import com.android.launcher3.testing.TestProtocol;
import com.android.launcher3.touch.WorkspaceTouchListener;
import com.android.launcher3.userevent.nano.LauncherLogProto.Action;
import com.android.launcher3.userevent.nano.LauncherLogProto.ContainerType;
@ -2547,7 +2546,7 @@ public class Workspace extends PagedView<WorkspacePageIndicator>
view = mLauncher.createShortcut(cellLayout, (WorkspaceItemInfo) info);
break;
case LauncherSettings.Favorites.ITEM_TYPE_FOLDER:
view = FolderIcon.fromXml(R.layout.folder_icon, mLauncher, cellLayout,
view = FolderIcon.inflateFolderAndIcon(R.layout.folder_icon, mLauncher, cellLayout,
(FolderInfo) info);
break;
default:

View File

@ -67,6 +67,7 @@ import com.android.launcher3.icons.DotRenderer;
import com.android.launcher3.touch.ItemClickHandler;
import com.android.launcher3.util.Executors;
import com.android.launcher3.util.Thunk;
import com.android.launcher3.views.ActivityContext;
import com.android.launcher3.views.IconLabelDotView;
import com.android.launcher3.widget.PendingAddShortcutInfo;
@ -79,7 +80,7 @@ import java.util.function.Predicate;
*/
public class FolderIcon extends FrameLayout implements FolderListener, IconLabelDotView {
@Thunk Launcher mLauncher;
@Thunk ActivityContext mActivity;
@Thunk Folder mFolder;
private FolderInfo mInfo;
@ -153,7 +154,21 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
mDotParams = new DotRenderer.DrawParams();
}
public static FolderIcon fromXml(int resId, Launcher launcher, ViewGroup group,
public static FolderIcon inflateFolderAndIcon(int resId, Launcher launcher, ViewGroup group,
FolderInfo folderInfo) {
Folder folder = Folder.fromXml(launcher);
folder.setDragController(launcher.getDragController());
FolderIcon icon = inflateIcon(resId, launcher, group, folderInfo);
folder.setFolderIcon(icon);
folder.bind(folderInfo);
icon.setFolder(folder);
icon.setOnFocusChangeListener(launcher.getFocusHandler());
return icon;
}
public static FolderIcon inflateIcon(int resId, ActivityContext activity, ViewGroup group,
FolderInfo folderInfo) {
@SuppressWarnings("all") // suppress dead code warning
final boolean error = INITIAL_ITEM_ANIMATION_DURATION >= DROP_IN_ANIMATION_DURATION;
@ -163,7 +178,7 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
"is dependent on this");
}
DeviceProfile grid = launcher.getWallpaperDeviceProfile();
DeviceProfile grid = activity.getWallpaperDeviceProfile();
FolderIcon icon = (FolderIcon) LayoutInflater.from(group.getContext())
.inflate(resId, group, false);
@ -177,27 +192,27 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
icon.setTag(folderInfo);
icon.setOnClickListener(ItemClickHandler.INSTANCE);
icon.mInfo = folderInfo;
icon.mLauncher = launcher;
icon.mActivity = activity;
icon.mDotRenderer = grid.mDotRendererWorkSpace;
icon.setContentDescription(launcher.getString(R.string.folder_name_format, folderInfo.title));
icon.setContentDescription(
group.getContext().getString(R.string.folder_name_format, folderInfo.title));
// Keep the notification dot up to date with the sum of all the content's dots.
FolderDotInfo folderDotInfo = new FolderDotInfo();
for (WorkspaceItemInfo si : folderInfo.contents) {
folderDotInfo.addDotInfo(launcher.getDotInfoForItem(si));
folderDotInfo.addDotInfo(activity.getDotInfoForItem(si));
}
icon.setDotInfo(folderDotInfo);
Folder folder = Folder.fromXml(launcher);
folder.setDragController(launcher.getDragController());
folder.setFolderIcon(icon);
folder.bind(folderInfo);
icon.setFolder(folder);
icon.setAccessibilityDelegate(launcher.getAccessibilityDelegate());
icon.setAccessibilityDelegate(activity.getAccessibilityDelegate());
icon.mPreviewVerifier = new FolderGridOrganizer(activity.getDeviceProfile().inv);
icon.mPreviewVerifier.setFolderInfo(folderInfo);
icon.updatePreviewItems(false);
folderInfo.addListener(icon);
icon.setOnFocusChangeListener(launcher.mFocusHandler);
return icon;
}
@ -225,9 +240,6 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
private void setFolder(Folder folder) {
mFolder = folder;
mPreviewVerifier = new FolderGridOrganizer(mLauncher.getDeviceProfile().inv);
mPreviewVerifier.setFolderInfo(mFolder.getInfo());
updatePreviewItems(false);
}
private boolean willAcceptItem(ItemInfo item) {
@ -309,14 +321,15 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
// Typically, the animateView corresponds to the DragView; however, if this is being done
// after a configuration activity (ie. for a Shortcut being dragged from AllApps) we
// will not have a view to animate
if (animateView != null) {
DragLayer dragLayer = mLauncher.getDragLayer();
if (animateView != null && mActivity instanceof Launcher) {
final Launcher launcher = (Launcher) mActivity;
DragLayer dragLayer = launcher.getDragLayer();
Rect from = new Rect();
dragLayer.getViewRectRelativeToSelf(animateView, from);
Rect to = finalRect;
if (to == null) {
to = new Rect();
Workspace workspace = mLauncher.getWorkspace();
Workspace workspace = launcher.getWorkspace();
// Set cellLayout and this to it's final state to compute final animation locations
workspace.setFinalTransitionTransform();
float scaleX = getScaleX();
@ -382,7 +395,7 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
String[] suggestedNameOut = new String[FolderNameProvider.SUGGEST_MAX];
if (FeatureFlags.FOLDER_NAME_SUGGEST.get()) {
Executors.UI_HELPER_EXECUTOR.post(() -> {
mLauncher.getFolderNameProvider().getSuggestedFolderName(
launcher.getFolderNameProvider().getSuggestedFolderName(
getContext(), mInfo.contents, suggestedNameOut);
showFinalView(finalIndex, item, suggestedNameOut);
});
@ -547,7 +560,7 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
if (!mForceHideDot && ((mDotInfo != null && mDotInfo.hasDot()) || mDotScale > 0)) {
Rect iconBounds = mDotParams.iconBounds;
BubbleTextView.getIconBounds(this, iconBounds,
mLauncher.getWallpaperDeviceProfile().iconSizePx);
mActivity.getWallpaperDeviceProfile().iconSizePx);
float iconScale = (float) mBackground.previewSize / iconBounds.width();
Utilities.scaleRectAboutCenter(iconBounds, iconScale);
@ -605,7 +618,7 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
@Override
public void onAdd(WorkspaceItemInfo item, int rank) {
boolean wasDotted = mDotInfo.hasDot();
mDotInfo.addDotInfo(mLauncher.getDotInfoForItem(item));
mDotInfo.addDotInfo(mActivity.getDotInfoForItem(item));
boolean isDotted = mDotInfo.hasDot();
updateDotScale(wasDotted, isDotted);
invalidate();
@ -615,7 +628,7 @@ public class FolderIcon extends FrameLayout implements FolderListener, IconLabel
@Override
public void onRemove(WorkspaceItemInfo item) {
boolean wasDotted = mDotInfo.hasDot();
mDotInfo.subtractDotInfo(mLauncher.getDotInfoForItem(item));
mDotInfo.subtractDotInfo(mActivity.getDotInfoForItem(item));
boolean isDotted = mDotInfo.hasDot();
updateDotScale(wasDotted, isDotted);
invalidate();

View File

@ -37,10 +37,10 @@ import android.widget.TextView;
import androidx.annotation.NonNull;
import com.android.launcher3.Launcher;
import com.android.launcher3.Utilities;
import com.android.launcher3.WorkspaceItemInfo;
import com.android.launcher3.graphics.PreloadIconDrawable;
import com.android.launcher3.views.ActivityContext;
import java.util.ArrayList;
import java.util.List;
@ -94,7 +94,8 @@ public class PreviewItemManager {
public PreviewItemManager(FolderIcon icon) {
mContext = icon.getContext();
mIcon = icon;
mIconSize = Launcher.getLauncher(mContext).getDeviceProfile().folderChildIconSizePx;
mIconSize = ActivityContext.lookupContext(
mContext).getDeviceProfile().folderChildIconSizePx;
}
/**
@ -132,7 +133,7 @@ public class PreviewItemManager {
mTotalWidth = totalSize;
mPrevTopPadding = mIcon.getPaddingTop();
mIcon.mBackground.setup(mIcon.mLauncher, mIcon.mLauncher, mIcon, mTotalWidth,
mIcon.mBackground.setup(mIcon.getContext(), mIcon.mActivity, mIcon, mTotalWidth,
mIcon.getPaddingTop());
mIcon.mPreviewLayoutRule.init(mIcon.mBackground.previewSize, mIntrinsicIconSize,
Utilities.isRtl(mIcon.getResources()));
@ -152,7 +153,7 @@ public class PreviewItemManager {
}
private PreviewItemDrawingParams getFinalIconParams(PreviewItemDrawingParams params) {
float iconSize = mIcon.mLauncher.getDeviceProfile().iconSizePx;
float iconSize = mIcon.mActivity.getDeviceProfile().iconSizePx;
final float scale = iconSize / mReferenceDrawable.getIntrinsicWidth();
final float trans = (mIcon.mBackground.previewSize - iconSize) / 2;

View File

@ -49,6 +49,7 @@ import android.widget.TextClock;
import com.android.launcher3.BubbleTextView;
import com.android.launcher3.CellLayout;
import com.android.launcher3.DeviceProfile;
import com.android.launcher3.FolderInfo;
import com.android.launcher3.Hotseat;
import com.android.launcher3.InsettableFrameLayout;
import com.android.launcher3.InvariantDeviceProfile;
@ -63,6 +64,7 @@ import com.android.launcher3.WorkspaceItemInfo;
import com.android.launcher3.WorkspaceLayoutManager;
import com.android.launcher3.allapps.SearchUiManager;
import com.android.launcher3.config.FeatureFlags;
import com.android.launcher3.folder.FolderIcon;
import com.android.launcher3.icons.BaseIconFactory;
import com.android.launcher3.icons.BitmapInfo;
import com.android.launcher3.icons.BitmapRenderer;
@ -239,6 +241,12 @@ public class LauncherPreviewRenderer implements Callable<Bitmap> {
addInScreenFromBind(icon, info);
}
private void inflateAndAddFolder(FolderInfo info) {
FolderIcon folderIcon = FolderIcon.inflateIcon(R.layout.folder_icon, this, mWorkspace,
info);
addInScreenFromBind(folderIcon, info);
}
private void dispatchVisibilityAggregated(View view, boolean isVisible) {
// Similar to View.dispatchVisibilityAggregated implementation.
final boolean thisVisible = view.getVisibility() == VISIBLE;
@ -288,7 +296,7 @@ public class LauncherPreviewRenderer implements Callable<Bitmap> {
inflateAndAddIcon((WorkspaceItemInfo) itemInfo);
break;
case LauncherSettings.Favorites.ITEM_TYPE_FOLDER:
// TODO: for folder implementation here.
inflateAndAddFolder((FolderInfo) itemInfo);
break;
default:
break;