一、项目代码地址:https://github.com/lingchen1854/Simple-Launch

二、效果图: gif动图可以进git查看,csdn上传失败。

          

三、代码分析:

1.先上一段简单的沉浸式代码。

private void initWindow() {Window window = getWindow();View decorView = window.getDecorView();int option = View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN| View.SYSTEM_UI_FLAG_LAYOUT_STABLE;decorView.setSystemUiVisibility(option);if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);window.setStatusBarColor(Color.TRANSPARENT);}}

2.获取所有带Launcher的app信息,装到一个ArrayList中:

    public static ArrayList<AppInfoModel> getLauncherInfo(Context context){ArrayList<AppInfoModel> mAppInfoModels = new ArrayList<>();PackageManager packageManager = context.getPackageManager();Intent mainIntent = new Intent(Intent.ACTION_MAIN, null);mainIntent.addCategory(Intent.CATEGORY_LAUNCHER);//筛选带launcher的List<ResolveInfo> apps = packageManager.queryIntentActivities(mainIntent, 0);for (int i = 0;i < apps.size();i++){ResolveInfo info = apps.get(i);try {AppInfoModel appInfoModel = new AppInfoModel();PackageInfo packageinfo = packageManager.getPackageInfo(info.activityInfo.applicationInfo.packageName, 0);appInfoModel.setAppName(String.valueOf(info.loadLabel(packageManager)));//应用名称appInfoModel.setVersionCode(String.valueOf(packageinfo.versionCode));//版本号appInfoModel.setVersionName(String.valueOf(packageinfo.versionName));//版本名appInfoModel.setPackageName(info.activityInfo.applicationInfo.packageName);//包名appInfoModel.setIcon(info.activityInfo.loadIcon(packageManager));//应用头像appInfoModel.setPackageClassName(info.activityInfo.name);//包类名,用于后面打开activityappInfoModel.setFirstInstallTime(stampToDate(packageinfo.firstInstallTime));//第一次应用安装的时间,不准确,没用上appInfoModel.setLastUpdateTime(stampToDate(packageinfo.lastUpdateTime));//最后一次更新的时间,不准确,没用上mAppInfoModels.add(appInfoModel);} catch (PackageManager.NameNotFoundException e) {e.printStackTrace();}}return mAppInfoModels;}

3.获取横竖屏状态:

mScreenFlag = getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE;//获取横竖屏状态

4.旋转屏幕前保存画廊、方格状态。

if (savedInstanceState != null && savedInstanceState.getBoolean("status")) {//获取旋转屏幕前的状态mCurLayoutManageFlag = true;textView.setText("画廊模式");initMoreRecyclerView();//初始化成方格模式
}else {initRecyclerView();//初始化成画廊模式
}@Override
protected void onSaveInstanceState(Bundle outState) {super.onSaveInstanceState(outState);outState.putBoolean("status", mCurLayoutManageFlag);//旋转屏幕时保存当前模式
}

5.RecyclerView画廊模式:

private void initRecyclerView() {Log.d(TAG, "initMoreRecyclerView: 切换画廊模式");CarouselLayoutManager layoutManager;if (mScreenFlag){//横屏layoutManager = new CarouselLayoutManager(CarouselLayoutManager.HORIZONTAL,true);//true循环轮播}else {//竖屏layoutManager = new CarouselLayoutManager(CarouselLayoutManager.VERTICAL,true);//true循环轮播}RecyclerViewAdapter recyclerViewAdapter = new RecyclerViewAdapter(this,mAppInfoModels,R.layout.rc_item);layoutManager.setPostLayoutListener(new CarouselZoomPostLayoutListener());mRecyclerView.setHasFixedSize(true);//item不会去改变RecyclerView宽高时调用mRecyclerView.addOnScrollListener(new CenterScrollListener());//给CarouselLayoutManager使用的,监听滑动状态变化mRecyclerView.setLayoutManager(layoutManager);mRecyclerView.setAdapter(recyclerViewAdapter);recyclerViewAdapter.setOnItemClickListener(onItemClickListener);}

6.RecyclerView方格模式,本来StaggeredGridLayoutManager是瀑布流模式,结果发现不好看,硬生生给用成了方格模式:

    private void initMoreRecyclerView() {Log.d(TAG, "initMoreRecyclerView: 切换方格模式");StaggeredGridLayoutManager staggeredGridLayoutManager;if (mScreenFlag){//横屏staggeredGridLayoutManager = new StaggeredGridLayoutManager(3,StaggeredGridLayoutManager.HORIZONTAL);}else {staggeredGridLayoutManager = new StaggeredGridLayoutManager(3,StaggeredGridLayoutManager.VERTICAL);}mRecyclerView.setLayoutManager(staggeredGridLayoutManager);RecyclerViewAdapter recyclerViewAdapter = new RecyclerViewAdapter(this,mAppInfoModels,R.layout.staggered_item);mRecyclerView.setAdapter(recyclerViewAdapter);recyclerViewAdapter.setOnItemClickListener(onItemClickListener);}

7.点击效果:

    private RecyclerViewAdapter.OnItemClickListener onItemClickListener = new RecyclerViewAdapter.OnItemClickListener() {@Overridepublic void onItemClick(int position) {AppInfoModel appInfoModel = mAppInfoModels.get(position);Intent intent = new Intent(Intent.ACTION_MAIN);intent.addCategory(Intent.CATEGORY_LAUNCHER);intent.setComponent(new ComponentName(appInfoModel.getPackageName(), appInfoModel.getPackageClassName()));intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);startActivity(intent);Log.d(TAG, "onItemClick: 打开应用 "+appInfoModel.getAppName());}@Overridepublic void onItemLongClick(int position) {Uri packageUri = Uri.parse("package:" + mAppInfoModels.get(position).getPackageName());Intent intent = new Intent(Intent.ACTION_DELETE, packageUri);startActivity(intent);Log.d(TAG, "onItemClick: 卸载应用 "+mAppInfoModels.get(position).getAppName());}};

8.下面那堆按钮的点击效果。

    private boolean mCurLayoutManageFlag = false;@Overridepublic void onClick(View v) {switch (v.getId()){case R.id.open_setting_id:Log.d(TAG, "onClick: 打开设置");Intent intent = new Intent(Settings.ACTION_SETTINGS);intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);startActivity(intent);overridePendingTransition(android.R.anim.fade_in, android.R.anim.fade_out);break;case R.id.update_id:Log.d(TAG, "onClick: 打开升级程序");try {Intent upgradeIntent = new Intent("android.com.likego.hph03_update.Main");upgradeIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);startActivity(upgradeIntent);overridePendingTransition(android.R.anim.fade_in, android.R.anim.fade_out);}catch (Exception e){e.printStackTrace();Toast.makeText(MainActivity.this,"没有升级程序",Toast.LENGTH_LONG).show();}break;case R.id.reset_id:Log.d(TAG, "onClick: 恢复出厂设置");AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);builder.setMessage("恢复出厂设置");builder.setNegativeButton("取消", null);builder.setPositiveButton("确认", new DialogInterface.OnClickListener() {@Overridepublic void onClick(DialogInterface dialog, int which) {Log.d(TAG, "onClick: 确认");sendBroadcast(new Intent("android.intent.action.MASTER_CLEAR"));}});builder.create().show();break;case R.id.cut_layoutManager_id:Log.d(TAG, "onClick: 切换模式");TextView textView = (TextView) v;if (mCurLayoutManageFlag){mCurLayoutManageFlag = false;initRecyclerView();textView.setText("方格模式");}else {mCurLayoutManageFlag = true;initMoreRecyclerView();textView.setText("画廊模式");}break;case R.id.start_Development_id:AppInfoUtils.startDevelopmentActivity(MainActivity.this);break;case R.id.show_xml_id:boolean status = AppInfoUtils.startUiTest(true);if (status){Toast.makeText(MainActivity.this,"显示成功,稍后生效",Toast.LENGTH_LONG).show();}else {Toast.makeText(MainActivity.this,"显示失败",Toast.LENGTH_LONG).show();}break;case R.id.hide_xml_id:status = AppInfoUtils.startUiTest(false);if (status){Toast.makeText(MainActivity.this,"关闭成功,稍后生效",Toast.LENGTH_LONG).show();}else {Toast.makeText(MainActivity.this,"关闭失败",Toast.LENGTH_LONG).show();}break;default:break;}}

9.RecyclerView的适配器。

package com.likego.backgrounddesktop;import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;import com.likego.backgrounddesktop.model.AppInfoModel;import java.util.ArrayList;/*** User: ap01854* Date: 2020/6/30* Time: 16:05:11*/
class RecyclerViewAdapter extends RecyclerView.Adapter<RecyclerViewAdapter.ViewHolder> {private ArrayList<AppInfoModel> mAppInfoModels;private LayoutInflater mInflater;private OnItemClickListener mOnItemClickListener;int mItemLayoutID;public interface OnItemClickListener {void onItemClick(int position);void onItemLongClick(int position);}public RecyclerViewAdapter(Context context, ArrayList<AppInfoModel> appInfoModels,int itemLayoutID) {mInflater = LayoutInflater.from(context);mAppInfoModels = appInfoModels;mItemLayoutID = itemLayoutID;}public void setOnItemClickListener(OnItemClickListener onItemClickListener) {this.mOnItemClickListener = onItemClickListener;}@NonNull@Overridepublic ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {return new ViewHolder(mInflater.inflate(mItemLayoutID, parent, false));}@Overridepublic void onBindViewHolder(@NonNull final ViewHolder holder, final int position) {holder.appName.setText(mAppInfoModels.get(position).getAppName());holder.versionName.setText("VN : "+mAppInfoModels.get(position).getVersionName());holder.versionCode.setText("VC : "+mAppInfoModels.get(position).getVersionCode());holder.icon.setImageDrawable(mAppInfoModels.get(position).getIcon());if (mOnItemClickListener != null){holder.item.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {mOnItemClickListener.onItemClick(position);}});holder.item.setOnLongClickListener(new View.OnLongClickListener() {@Overridepublic boolean onLongClick(View v) {mOnItemClickListener.onItemLongClick(position);return false;}});}}@Overridepublic int getItemCount() {return mAppInfoModels.size();}public static class ViewHolder extends RecyclerView.ViewHolder{LinearLayout item;TextView appName;TextView versionName;TextView versionCode;ImageView icon;public ViewHolder(@NonNull View itemView) {super(itemView);item = itemView.findViewById(R.id.rc_item);appName = itemView.findViewById(R.id.app_name_id);versionName = itemView.findViewById(R.id.version_name_id);versionCode = itemView.findViewById(R.id.version_code_id);icon = itemView.findViewById(R.id.icon_id);}}}

10.item圆角透明布局:

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"android:shape="rectangle"><corners android:radius="30dp"/><gradientandroid:angle="45"android:endColor="#0Fffffff"android:startColor="#0Fffffff"></gradient>
</shape>

11.主界面部件:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools"android:background="@drawable/launcher_bg"android:layout_width="match_parent"android:layout_height="match_parent"tools:context=".MainActivity"><HorizontalScrollViewandroid:layout_alignParentBottom="true"android:layout_margin="10dp"android:scrollbars="none"android:layout_width="match_parent"android:layout_height="wrap_content"><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"><Button android:id="@+id/open_setting_id"android:background="@drawable/button_kt_touch"android:text="@string/open_setting"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/><Button android:id="@+id/update_id"android:background="@drawable/button_kt_touch"android:text="@string/update"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/><Button android:id="@+id/reset_id"android:background="@drawable/button_kt_touch"android:text="@string/reset"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/><Button android:id="@+id/cut_layoutManager_id"android:background="@drawable/button_kt_touch"android:text="@string/change"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/><Button android:id="@+id/start_Development_id"android:background="@drawable/button_kt_touch"android:text="@string/start_development"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/><Button android:id="@+id/show_xml_id"android:background="@drawable/button_kt_touch"android:text="@string/show_xml"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/><Button android:id="@+id/hide_xml_id"android:background="@drawable/button_kt_touch"android:text="@string/hide_xml"android:textSize="@dimen/bottom_button_textSize"android:textColor="@color/textViewColor"android:layout_marginStart="@dimen/bottom_button_layout_marginStart"android:layout_width="@dimen/bottom_button_width"android:layout_height="@dimen/bottom_button_height"/></LinearLayout></HorizontalScrollView><androidx.recyclerview.widget.RecyclerViewandroid:id="@+id/launcher_rv_id"android:layout_marginTop="20dp"android:layout_marginBottom="50dp"android:overScrollMode="never"android:layout_width="match_parent"android:layout_height="match_parent"/></RelativeLayout>

12.画廊模式的item布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"android:background="@drawable/bg_scrim_shape"android:orientation="vertical"android:gravity="center"android:id="@+id/rc_item"android:layout_width="@dimen/item_layout_width_height"android:layout_height="@dimen/item_layout_width_height"><TextView android:id="@+id/app_name_id"android:gravity="center"android:textSize="@dimen/item_title_textSize"android:textColor="@color/textViewColor"android:background="@drawable/set_dialog_title_bg"android:layout_width="match_parent"android:layout_height="50dp"/><Viewandroid:layout_weight="1"android:layout_width="0dp"android:layout_height="0dp"/><ImageView android:id="@+id/icon_id"android:layout_width="@dimen/item_icon_width_height"android:layout_height="@dimen/item_icon_width_height"/><Viewandroid:layout_weight="1"android:layout_width="0dp"android:layout_height="0dp"/><LinearLayoutandroid:layout_margin="10dp"android:orientation="vertical"android:layout_width="match_parent"android:layout_height="wrap_content"><TextView android:id="@+id/version_code_id"android:gravity="center"android:textSize="@dimen/item_version_textSize"android:textColor="@color/textViewColor"android:layout_width="match_parent"android:layout_height="wrap_content"/><TextView android:id="@+id/version_name_id"android:gravity="center"android:textSize="@dimen/item_version_textSize"android:textColor="@color/textViewColor"android:layout_width="match_parent"android:layout_height="wrap_content"/></LinearLayout></LinearLayout>

13.方格模式的item布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"android:orientation="vertical"android:background="@drawable/bg_scrim_shape"android:id="@+id/rc_item"android:gravity="center"android:layout_margin="5dp"android:layout_width="@dimen/staggered_item_layout_width_height"android:layout_height="@dimen/staggered_item_layout_width_height"><TextView android:id="@+id/app_name_id"android:gravity="center"android:textSize="@dimen/staggered_item_title_textSize"android:textColor="@color/textViewColor"android:background="@drawable/set_dialog_title_bg"android:layout_width="match_parent"android:layout_height="25dp"/><Viewandroid:layout_weight="1"android:layout_width="0dp"android:layout_height="0dp"/><ImageView android:id="@+id/icon_id"android:layout_width="@dimen/staggered_item_icon_width_height"android:layout_height="@dimen/staggered_item_icon_width_height"/><Viewandroid:layout_weight="1"android:layout_width="0dp"android:layout_height="0dp"/><LinearLayoutandroid:layout_marginBottom="5dp"android:orientation="vertical"android:layout_width="match_parent"android:layout_height="wrap_content"><TextView android:id="@+id/version_code_id"android:gravity="center"android:textSize="@dimen/staggered_item_version_textSize"android:textColor="@color/textViewColor"android:layout_width="match_parent"android:layout_height="wrap_content"/><TextView android:id="@+id/version_name_id"android:gravity="center"android:textSize="@dimen/staggered_item_version_textSize"android:textColor="@color/textViewColor"android:layout_width="match_parent"android:layout_height="wrap_content"/></LinearLayout></LinearLayout>

android - 简易launcher - RecyclerView画廊模式相关推荐

  1. 从源码角度看Android系统Launcher在开机时的启动过程

    Launcher是Android所有应用的入口,用来显示系统中已经安装的应用程序图标. Launcher本身也是一个App,一个提供桌面显示的App,但它与普通App有如下不同: Launcher是所 ...

  2. android q桌面,Android Q带来全新桌面模式

    原标题:Android Q带来全新桌面模式 IT之家3月14日消息 谷歌在美国当地时间3月13日(北京时间14日凌晨)正式推送了Android Q的首个Beta版本,"亲儿子"Pi ...

  3. Android 控件 RecyclerView 看这篇就够了

    [Android 控件 RecyclerView] 概述 RecyclerView是什么 从Android 5.0开始,谷歌公司推出了一个用于大量数据展示的新控件RecylerView,可以用来代替传 ...

  4. Android 控件 RecyclerView

    [Android 控件 RecyclerView] 概述 RecyclerView是什么 从Android 5.0开始,谷歌公司推出了一个用于大量数据展示的新控件RecylerView,可以用来代替传 ...

  5. Android简易音乐重构MVVM Java版-新增推荐菜单及侧边栏展示(十二)

    Android简易音乐重构MVVM Java版-新增推荐菜单及侧边栏展示(十二) 关于 效果图 添加侧边栏 添加推荐歌单 新增RecommendAdapter适配器 修改DiscoverFragmen ...

  6. android天气搜索框,Android简易天气App

    原标题:Android简易天气App 前言 本打算是写一个贝塞尔曲线的demo,想了一下哪种场景可以直观的表现出贝塞尔曲线,想到天气预报中的那些24小时和未来几日天气变化正好适用.接着开始构思,开始是 ...

  7. Android简易音乐重构MVVM Java版-新增推荐雷达歌单及重构首页(十三)

    Android简易音乐重构MVVM Java版-新增推荐雷达歌单及重构首页(十三) 关于 效果图 修改ApiService 添加HomeDiscoverEntity实体类 添加BannerExtInf ...

  8. Android简易音乐重构MVVM Java版-新增歌曲播放界面+状态栏黑科技(十七)

    Android简易音乐重构MVVM Java版-新增歌曲播放界面(十七) 关于 效果 新增歌曲播放界面 增加歌词view `LyricView` 修改ApiService 添加引用 添加SongPla ...

  9. Android简易音乐重构MVVM Java版-新增推荐、雷达歌单详情列表界面(十八)

    Android简易音乐重构MVVM Java版-新增推荐.雷达歌单详情列表界面(十八) 关于 效果 修改ApiService 增加歌单列表实体类RecommendListEntity 新增歌单列表界面 ...

最新文章

  1. VS如何将核心函数封装成dll、lib,并供给第三方调用?
  2. VM 7 下ubuntu安装vmtools
  3. 八进制数输出二进制c语言,C语言 某数输出二进制的某位
  4. 「中间件系列一」kafka消息中间件
  5. Linux中Shell的转义用法笔记
  6. 软件项目管理-构建之法-四周总结
  7. 陷阱房图纸_揭秘户型图 | 研究了100个户型图后,我发现了这4个重大陷阱
  8. [CLR团队公告]CLR基础研究团队纲领
  9. 前端视频截图的方法canvas.drawImage()
  10. btr如何修改服务器手机版我的世界,我的世界btr编辑器
  11. Maven引入数据库JDBC驱动
  12. 揭秘Apple Watch心率监测技术
  13. HTTP Error 500.30 - ANCM In-Process Start Failure 解决方法
  14. html中点重置和提交没反应,网页点提交按钮没反应 js提交表单,点击按钮无反应...
  15. 洛谷P4518 [JSOI2018]绝地反击(计算几何+二分图+退流)
  16. 软硬件测试策略及方法
  17. [经典之作]vml经典之作
  18. (Java实习生)每日10道面试题打卡——JavaWeb篇
  19. HaaS学习笔记 | 阿里云物联网平台的产品和设备创建明细教程
  20. ANSYS 有限元分析 后处理 General Postproc

热门文章

  1. 服务器操作系统该选 Debian/Ubuntu 还是 CentOS?
  2. 机器学习算法整理(六)— 贝叶斯算法_实现拼写检查器
  3. 测绘专业c语言程序,2017年武汉大学测绘遥感信息工程国家重点实验室968C语言程序设计[专业硕士]考研导师圈点必考题汇编...
  4. 可变气门升程的全球与中国市场2022-2028年:技术、参与者、趋势、市场规模及占有率研究报告
  5. 上班迟到致失业,罪魁祸首在于这个 App 的 Bug!
  6. 移动端和pc端微信加入群聊
  7. linux-鸟哥私房菜,基础命令全掌握
  8. 【产品】产品设计:折纸说明书纸张设计要求
  9. linux Runtime
  10. 使用Unity UGUI根据实时数据动态绘制图线(心电图)