android 9.0 launcher3 去掉抽屉式显示所有 app(代码详解)
效果图
修改思路
1、增加全局控制变量sys.launcher3.is_full_app,用来动态切换
2、增加两套布局,对应有抽屉和无抽屉
3、去除allAppsButton
4、将AllAppsContainerView中的图标加载到Workspace
5、新安装的app自动添加图标到Workspace
6、替换Workspace图标长按删除选项为取消
7、屏蔽上拉显示抽屉页面手势
8、修改页面指示线为圆点
上代码
1、增加全局控制变量sys.launcher3.is_full_app
1)在LauncherAppState中增加静态方法isDisableAllApps(),通过修改Settings中自定义的值sys.launcher3.is_full_app
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\LauncherAppState.java
privatestaticContextmContext; publicstaticbooleanisDisableAllApps(){ if(mContext!=null){ returnSettings.System.getInt(mContext.getContentResolver(), "sys.launcher3.is_full_app",0)==1; } returntrue; }
vendor\mediatek\proprietary\packages\apps\Launcher3\AndroidManifest-common.xml
2)AndroidManifest-common.xml中增加权限
3)在SettingsActivity中增加SwitchPreference用以动态修改sys.launcher3.is_full_app
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\SettingsActivity.java
在内部类LauncherSettingsFragment中重写onPreferenceTreeClick()用以监听SwitchPreference点击
/** *Thisfragmentshowsthelauncherpreferences. */ publicstaticclassLauncherSettingsFragmentextendsPreferenceFragment{ ..... @Override publicvoidonCreate(BundlesavedInstanceState){ super.onCreate(savedInstanceState); .... //读取保存的值,初始化SwitchPreference的初始状态,是否选中 intisFull=Settings.System.getInt(getActivity().getContentResolver(), "sys.launcher3.is_full_app",0); Log.d("Launcher3","sys.launcher3.is_full_app="+isFull); SwitchPreferencefullSwitch=(SwitchPreference)findPreference("pref_is_full_app"); fullSwitch.setChecked(isFull==1); } //addforchangeis_full_appvalue @Override publicbooleanonPreferenceTreeClick(PreferenceScreenpreferenceScreen,Preferencepreference){ booleanresult=true; finalStringkey=preference.getKey(); if("pref_is_full_app".equals(key)){ booleanchecked=((SwitchPreference)preference).isChecked(); Settings.System.putInt(getActivity().getContentResolver(),"sys.launcher3.is_full_app", checked?1:0); Log.e("Launcher3","SwitchPreferencechecked="+checked); //Valuehaschanged ProgressDialog.show(getActivity(), null/*title*/, getActivity().getString(R.string.full_app_override_progress), true/*indeterminate*/, false/*cancelable*/); newLooperExecutor(LauncherModel.getWorkerLooper()).execute( newOverrideApplyHandler(getActivity())); } returnresult; } }
点击SwitchPreference后需要保存sys.launcher3.is_full_app新值,同时清除Launcher3的缓存,延时启动并结束当前进程
清除缓存方法clearApplicationUserData在Launcher3中编译报错,所以通过发送广播到Setting中进行真正的清缓存操作
//addforchangeis_full_appvalue privatestaticclassOverrideApplyHandlerimplementsRunnable{ privatefinalContextmContext; privateOverrideApplyHandler(Contextcontext){ mContext=context; } @Override publicvoidrun(){ //Cleartheiconcache. LauncherAppState.getInstance(mContext).getIconCache().clear(); //Waitforit try{ Thread.sleep(1000); }catch(Exceptione){ Log.e("Launcher3","Errorwaiting",e); } //Scheduleanalarmbeforewekillourself. IntenthomeIntent=newIntent(Intent.ACTION_MAIN) .addCategory(Intent.CATEGORY_HOME) .setPackage(mContext.getPackageName()) .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); PendingIntentpi=PendingIntent.getActivity(mContext,42, homeIntent,PendingIntent.FLAG_CANCEL_CURRENT|PendingIntent.FLAG_ONE_SHOT); mContext.getSystemService(AlarmManager.class).setExact( AlarmManager.ELAPSED_REALTIME,SystemClock.elapsedRealtime()+50,pi); //cleardatawillkillprocess Intentintent=newIntent("com.android.action.CLEAR_APP_DATA"); intent.putExtra("pkgName","com.android.launcher3"); intent.addFlags(0x01000000); mContext.sendBroadcast(intent); Log.i("Launcher3","Clearinguserdatacom.android.launcher3"); //Killprocess android.os.Process.killProcess(android.os.Process.myPid()); } }
4)SettingsActivity对应的xml文件修改launcher_preferences
vendor\mediatek\proprietary\packages\apps\Launcher3\res\xml\launcher_preferences.xml
对应的string文件就不贴了,自己增加下就行
2、增加两套布局,对应有抽屉和无抽屉
加载布局文件对应的xml为vendor\mediatek\proprietary\packages\apps\Launcher3\res\xml\device_profiles.xml
Launcher3通过获取minWidthDps和minHeightDps来确定加载哪一个profile,我的平板分辨率是1280*800的,增加两个profile节点
对应的你需要在xml文件下增加4个文件,分别是default_workspace_tb_5x6.xmldw_hotseat_tb.xmldefault_workspace_tb_5x6_no_all_app.xmldw_hotseat_tb_no_all_app.xml
这样的好处是你可以自定义不同的布局文件加载内容,上面的配置含义简单说一下,分别是最小宽度、最小高度、布局的行和列、文件夹中布局行和列、图标大小、图标文字大小、HotSeat个数,加载的布局文件
在InvariantDeviceProfile()判断是否需要加载Tablet_no_all_appprofile
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\InvariantDeviceProfile.java
publicInvariantDeviceProfile(Contextcontext){ WindowManagerwm=(WindowManager)context.getSystemService(Context.WINDOW_SERVICE); Displaydisplay=wm.getDefaultDisplay(); DisplayMetricsdm=newDisplayMetrics(); display.getMetrics(dm); PointsmallestSize=newPoint(); PointlargestSize=newPoint(); display.getCurrentSizeRange(smallestSize,largestSize); //Thisguaranteesthatwidth3、去除allAppsButton
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\Hotseat.java
将resetLayout()中FeatureFlags.NO_ALL_APPS_ICON替换为LauncherAppState.isDisableAllApps()
voidresetLayout(booleanhasVerticalHotseat){ mContent.removeAllViewsInLayout(); mHasVerticalHotseat=hasVerticalHotseat; InvariantDeviceProfileidp=mLauncher.getDeviceProfile().inv; if(hasVerticalHotseat){ mContent.setGridSize(1,idp.numHotseatIcons); }else{ mContent.setGridSize(idp.numHotseatIcons,1); } //if(!FeatureFlags.NO_ALL_APPS_ICON){ ///addforcheckisneedallappbutton if(!LauncherAppState.isDisableAllApps()){ //AddtheAppsbutton Contextcontext=getContext(); DeviceProfilegrid=mLauncher.getDeviceProfile(); ... }4、将AllAppsContainerView中的图标加载到Workspace
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\model\LoaderTask.java
run()中增加判断,添加verifyApplications(),修改InstallShortcutReceiver中PendingInstallShortcutInfo为public
publicvoidrun(){ synchronized(this){ //Skipfastifwearealreadystopped. if(mStopped){ return; } } .... //secondstep TraceHelper.partitionSection(TAG,"step2.1:loadingallapps"); loadAllApps(); //addforloadallapponworkspace if(LauncherAppState.isDisableAllApps()){ android.util.Log.e("Launcher3","verifyApplications()"); verifyApplications(); } .... } //addforloadallapponworkspace privatevoidverifyApplications(){ finalContextcontext=mApp.getContext(); ArrayList>installQueue=newArrayList<>(); finalList profiles=mUserManager.getUserProfiles(); for(UserHandleuser:profiles){ finalList apps=mLauncherApps.getActivityList(null,user); ArrayList added=newArrayList (); synchronized(this){ for(LauncherActivityInfoapp:apps){ InstallShortcutReceiver.PendingInstallShortcutInfopendingInstallShortcutInfo=newInstallShortcutReceiver.PendingInstallShortcutInfo(app,context); added.add(pendingInstallShortcutInfo); installQueue.add(pendingInstallShortcutInfo.getItemInfo()); } } if(!added.isEmpty()){ mApp.getModel().addAndBindAddedWorkspaceItems(installQueue); } } } vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\model\BaseModelUpdateTask.java
注释run()中的return
@Override publicfinalvoidrun(){ if(!mModel.isModelLoaded()){ if(DEBUG_TASKS){ Log.d(TAG,"Ignoringmodeltasksinceloaderispending="+this); } //Loaderhasnotyetrun. //annotaionforloadallapponworkspace //return; } execute(mApp,mDataModel,mAllAppsList); }5、新安装的app自动添加图标到Workspace
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\model\PackageUpdatedTask.java
execute()中增加判断,添加updateToWorkSpace()
publicvoidexecute(LauncherAppStateapp,BgDataModeldataModel,AllAppsListappsList){ .... finalArrayListaddedOrModified=newArrayList<>(); addedOrModified.addAll(appsList.added); //addforloadnewinstallapponworkspace if(LauncherAppState.isDisableAllApps()){ android.util.Log.e("cczLauncher3","updateToWorkSpace()"); updateToWorkSpace(context,app,appsList); } ... } //addforloadnewinstallapponworkspace publicvoidupdateToWorkSpace(Contextcontext,LauncherAppStateapp,AllAppsListappsList){ ArrayList >installQueue=newArrayList<>(); finalList profiles=UserManagerCompat.getInstance(context).getUserProfiles(); ArrayList added =newArrayList (); for(UserHandleuser:profiles){ finalList apps=LauncherAppsCompat.getInstance(context).getActivityList(null,user); synchronized(this){ for(LauncherActivityInfoinfo:apps){ for(AppInfoappInfo:appsList.added){ if(info.getComponentName().equals(appInfo.componentName)){ InstallShortcutReceiver.PendingInstallShortcutInfomPendingInstallShortcutInfo =newInstallShortcutReceiver.PendingInstallShortcutInfo(info,context); added.add(mPendingInstallShortcutInfo); installQueue.add(mPendingInstallShortcutInfo.getItemInfo()); } } } } } if(!added.isEmpty()){ app.getModel().addAndBindAddedWorkspaceItems(installQueue); } } 6、替换Workspace图标长按删除选项为取消
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\DeleteDropTarget.java
在setTextBasedOnDragSource()、setControlTypeBasedOnDragSource()、onAccessibilityDrop()中分别增加判断是否需要删除图标
privatevoidsetTextBasedOnDragSource(ItemInfoitem){ if(!TextUtils.isEmpty(mText)){ mText=getResources().getString(item.id!=ItemInfo.NO_ID ?R.string.remove_drop_target_label :android.R.string.cancel); //addforhidedeletedroptarget if(LauncherAppState.isDisableAllApps()){ android.util.Log.e("Launcher3","hidedeletedroptarget"); mText=getResources().getString(isCanDrop(item) ?R.string.remove_drop_target_label :android.R.string.cancel); } requestLayout(); } } privatevoidsetControlTypeBasedOnDragSource(ItemInfoitem){ mControlType=item.id!=ItemInfo.NO_ID?ControlType.REMOVE_TARGET :ControlType.CANCEL_TARGET; //addforhidedeletedroptarget[S] if(LauncherAppState.isDisableAllApps()){ mControlType=isCanDrop(item)?ControlType.REMOVE_TARGET :ControlType.CANCEL_TARGET; } } publicvoidonAccessibilityDrop(Viewview,ItemInfoitem){ //Removetheitemfromlauncherandthedb,wecanignorethecontainerInfointhiscall //becausewealreadyremovethedragviewfromthefolder(ifthedragoriginatedfrom //afolder)inFolder.beginDrag() //addifjugeisneedremoveitemfromworkspace if(!LauncherAppState.isDisableAllApps()||isCanDrop(item)){ mLauncher.removeItem(view,item,true/*deleteFromDb*/); mLauncher.getWorkspace().stripEmptyScreens(); mLauncher.getDragLayer() .announceForAccessibility(getContext().getString(R.string.item_removed)); } } privatebooleanisCanDrop(ItemInfoitem){ return!(item.itemType==LauncherSettings.Favorites.ITEM_TYPE_APPLICATION|| item.itemType==LauncherSettings.Favorites.ITEM_TYPE_FOLDER); }vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3\dragndrop\DragController.java
drop()中增加判断,取消当前拖拽操作
privatevoiddrop(DropTargetdropTarget,RunnableflingAnimation){ .... booleanaccepted=false; if(dropTarget!=null){ dropTarget.onDragExit(mDragObject); if(dropTarget.acceptDrop(mDragObject)){ if(flingAnimation!=null){ flingAnimation.run(); }else{ dropTarget.onDrop(mDragObject,mOptions); } accepted=true; //addforcancelcanceldroptargethandle if(LauncherAppState.isDisableAllApps()&&dropTargetinstanceofDeleteDropTarget&& isNeedCancelDrag(mDragObject.dragInfo)){ cancelDrag(); } } } ... } privatebooleanisNeedCancelDrag(ItemInfoitem){ return(item.itemType==LauncherSettings.Favorites.ITEM_TYPE_APPLICATION|| item.itemType==LauncherSettings.Favorites.ITEM_TYPE_FOLDER); }7、屏蔽上拉显示抽屉页面手势
vendor\mediatek\proprietary\packages\apps\Launcher3\quickstep\src\com\android\launcher3\uioverrides\OverviewToAllAppsTouchController.java
canInterceptTouch()中增加判断是否直接拦截 @Override protectedbooleancanInterceptTouch(MotionEventev){ //addforforbiddenworkspacedragchangeGradientViewalph if(LauncherAppState.isDisableAllApps()){ android.util.Log.e("Launcher3","canInterceptTouch()"); returnfalse; } if(mCurrentAnimation!=null){ //Ifwearealreadyanimatingfromapreviousstate,wecanintercept. returntrue; } if(AbstractFloatingView.getTopOpenView(mLauncher)!=null){ returnfalse; } if(mLauncher.isInState(ALL_APPS)){ //Inall-appsonlylistenifthecontainercannotscrollitself returnmLauncher.getAppsView().shouldContainerScroll(ev); }elseif(mLauncher.isInState(NORMAL)){ returntrue; }elseif(mLauncher.isInState(OVERVIEW)){ RecentsViewrv=mLauncher.getOverviewPanel(); returnev.getY()>(rv.getBottom()-rv.getPaddingBottom()); }else{ returnfalse; } }8、修改页面指示线为圆点
vendor\mediatek\proprietary\packages\apps\Launcher3\res\layout\launcher.xml
WorkspacePageIndicator改为PageIndicatorDots
vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3 \pageindicators\PageIndicatorDots.java
增加PageIndicatorDots继承Insettable,复写setInsets(),调整圆点的位置
publicclassPageIndicatorDotsextendsViewimplementsPageIndicator,Insettable{ //addforchangeWorkspacePageIndicatorlinetodot @Override publicvoidsetInsets(Rectinsets){ DeviceProfilegrid=mLauncher.getDeviceProfile(); FrameLayout.LayoutParamslp=(FrameLayout.LayoutParams)getLayoutParams(); if(grid.isVerticalBarLayout()){ Rectpadding=grid.workspacePadding; lp.leftMargin=padding.left+grid.workspaceCellPaddingXPx; lp.rightMargin=padding.right+grid.workspaceCellPaddingXPx; lp.bottomMargin=padding.bottom; }else{ lp.leftMargin=lp.rightMargin=0; lp.gravity=Gravity.CENTER_HORIZONTAL|Gravity.BOTTOM; lp.bottomMargin=grid.hotseatBarSizePx+insets.bottom; } setLayoutParams(lp); } @Override publicvoidsetScroll(intcurrentScroll,inttotalScroll){ if(mNumPages>1){ if(mIsRtl){ currentScroll=totalScroll-currentScroll; } intscrollPerPage=totalScroll/(mNumPages-1); //addforchangeWorkspacePageIndicatorlinetodot if(scrollPerPage==0){ return; } intpageToLeft=currentScroll/scrollPerPage; intpageToLeftScroll=pageToLeft*scrollPerPage; intpageToRightScroll=pageToLeftScroll+scrollPerPage; ... }vendor\mediatek\proprietary\packages\apps\Launcher3\src\com\android\launcher3
\states\SpringLoadedState.java
注释setShouldAutoHide(),避免长按workSpace时发生崩溃
@Override publicvoidonStateEnabled(Launcherlauncher){ Workspacews=launcher.getWorkspace(); ws.showPageIndicatorAtCurrentScroll(); //annotaionforWorkspacePageIndicatorlinetodot //ws.getPageIndicator().setShouldAutoHide(false); //PreventanyUn/InstallShortcutReceiversfromupdatingthedbwhileweare //inspringloadedmode InstallShortcutReceiver.enableInstallQueue(InstallShortcutReceiver.FLAG_DRAG_AND_DROP); launcher.getRotationHelper().setCurrentStateRequest(REQUEST_LOCK); } @Override publicvoidonStateDisabled(finalLauncherlauncher){ //annotaionforWorkspacePageIndicatorlinetodot //launcher.getWorkspace().getPageIndicator().setShouldAutoHide(true); //Re-enableanyUn/InstallShortcutReceiverandnowprocessanyqueueditems InstallShortcutReceiver.disableAndFlushInstallQueue( InstallShortcutReceiver.FLAG_DRAG_AND_DROP,launcher); }总结
以上所述是小编给大家介绍的android9.0launcher3去掉抽屉式显示所有app代码详解,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对毛票票网站的支持!
如果你觉得本文对你有帮助,欢迎转载,烦请注明出处,谢谢!声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。