在开发道路上磕磕碰碰,我们踩坑填坑while(true)的过程中,大家都知道~规范的编写,良好的封装都会大大减少我们开发的时间提高开发效率,汲取了前辈的经验, 今天在这里跟大家分享我自己封装的BaseActivity,希望对大家有所帮助先来看看我们的BaseActivity有啥功能吧
1:避免findViewById的啰嗦操作,一行代码搞定页面OnClickListener点击事件
2:默认头布局,避免头布局include粘来粘去
3:其他一些:对状态栏的操作,页面跳转的封装等等等等....
在这里说一下,为了解决适配的问题,我最顶层基类是继承鸿洋大佬的AutoLayoutActivity
传送门:https:///hongyangAndroid/AndroidAutoLayout
下面开始本文正文。
直接一股脑的上代码balabala讲原理是一件很无趣的事情,但是很多时候又不得不这么做
我的baseActivity分为父子层,最里面试父层,提供页面跳转,状态栏控制,加载数据Dialog的控制功能
第二层儿子层为对头布局,内容布局的UI的控制做处理的功能
先看看GodBaseActivity里都有啥
public abstract class GodBaseActivity extends AutoLayoutActivity {
protected Intent mIntent;
protected LoadProgressDialog mLoadProgressDialog;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mIntent = new Intent();
onGodCreate(savedInstanceState);
setTranslucentStatus();
ActivityManagement.getInstance().addActivity(this);
}
//判断当前设备版本号是否为4.4以上,如果是,则通过调用setTranslucentStatus让状态栏变透明
protected void setTranslucentStatus() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
setTranslucentStatus(true);
}
}
protected abstract void onGodCreate(Bundle savedInstanceState);
public void toast(String text) {
if (text != null) {
Toast.makeText(this, text, Toast.LENGTH_SHORT).show();
}
}
public void showProgress() {
if (mLoadProgressDialog == null) mLoadProgressDialog = new LoadProgressDialog(this);
if (mLoadProgressDialog.isShowing()) return;
mLoadProgressDialog.show();
}
public void showProgress(String text) {
if (mLoadProgressDialog == null) mLoadProgressDialog = new LoadProgressDialog(this);
if (mLoadProgressDialog.isShowing()) return;
mLoadProgressDialog.setText(text);
mLoadProgressDialog.show();
}
public void dismissProgress() {
if (mLoadProgressDialog == null) return;
if (mLoadProgressDialog.isShowing())
mLoadProgressDialog.dismiss();
}
protected void skipActivity(Class cls, int ResultCode) {
mIntent.setClass(this, cls);
startActivityForResult(mIntent, ResultCode);
}
public void skipActivity(Class cls) {
mIntent.setClass(this, cls);
startActivity(mIntent);
}
protected void skipActivityFinish(Class cls) {
mIntent.setClass(this, cls);
startActivity(mIntent);
finish();
}
protected void skipActivityFinish(Class cls, int ResultCode) {
mIntent.setClass(this, cls);
startActivityForResult(mIntent, ResultCode);
finish();
}
@Override
protected void onDestroy() {
super.onDestroy();
ActivityManagement.getInstance().removeActivity(this);
}
/**
* 获取当前设备状态栏高度
*
* @return
*/
public int getStatusBarHeight() {
int result = 0;
int resourceId = getResources().getIdentifier("status_bar_height", "dimen", "android");
if (resourceId > 0) {
result = getResources().getDimensionPixelSize(resourceId);
}
return result;
}
/**
* 设置状态栏透明
*
* @param on
*/
@TargetApi(19)
private void setTranslucentStatus(boolean on) {
Window win = getWindow();
WindowManager.LayoutParams winParams = win.getAttributes();
final int bits = WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
if (on) {
winParams.flags |= bits;
} else {
winParams.flags &= ~bits;
}
win.setAttributes(winParams);
}
}
首先当然是让子层继承父层GodBaseActivity,然后我们在这里做对UI的控制操作,父activity是抽象的,实现了onGodCreate方法后我们在这里进行操作:
第一步:先创建一个布局,这个布局作为全局的父布局 activity_base,布局的内容如下:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http:///apk/res/android"
android:id="@+id/godbase_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/theme"
android:orientation="vertical">
<View
android:id="@+id/basestatus_view"
android:layout_width="match_parent"
android:layout_height="0dp" />
<RelativeLayout
android:id="@+id/basetop_view"
android:layout_width="match_parent"
android:layout_height="125px">
<ImageView
android:id="@+id/baseback_img"
android:layout_width="64px"
android:layout_height="64px"
android:layout_centerVertical="true"
android:layout_marginLeft="40px"
android:padding="7px"
android:src="@mipmap/ico_back" />
<TextView
android:id="@+id/basetitle_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerInParent="true"
android:textColor="#ffffff"
android:textSize="42px" />
</RelativeLayout>
<FrameLayout
android:id="@+id/content_view"
android:layout_width="match_parent"
android:layout_height="match_parent"></FrameLayout>
</LinearLayout>
当然有用!而且有大作用,我们先把这布局塞进去,在onGodCreate方法中直接 setContentView(R.layout.activity_base); 就好了,我们第一步先把状态栏给搞了,布局中id为basestatus_view就是我们作为状态栏背景的View我们写个方法给它高度 :
//将状态栏高度赋给basestatus_view
private void resetStatusViewHeight() {
basestatus_view = findViewById(.basestatus_view);
int statusheight = getStatusBarHeight();
if (statusheight != -1) {
LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, statusheight);
basestatus_view.setLayoutParams(params);
}
}
然后在onGodCreate中调用它,接下来我们去搞定头布局
头布局是啥?我们随便去个APP偷张图来看吧
红色框框起来的就是头布局,在我们的应用中几乎都会有一个这玩意,很多人都是写一个布局装它,然后再include去用它,我们当然不这样用,先把GodLeftHandBaseActivity也弄成抽象的,然后再搞俩抽象方法出来
protected abstract int setContentLayoutId();
protected abstract void init(Bundle savedInstanceState);
然后扔着不动先,再写一个普通方法出来
//初始化头布局
protected void initTopView() {
View view = LayoutInflater.from(this).inflate(setContentLayoutId(), null, false);
ViewGroup.LayoutParams layoutParams = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
view.setLayoutParams(layoutParams);
FrameLayout content_view = (FrameLayout) findViewById(.content_view);
content_view.addView(view);
basetop_view = findViewById(.basetop_view);
baseback_img = (ImageView) findViewById(.baseback_img);
basetitle_tv = (TextView) findViewById(.basetitle_tv);
godbase_view = findViewById(.godbase_view);
findViewById(.baseback_img).setOnClickListener(this);
}
然后再调用它,此时我们的GodLeftHandBaseActivity全部内容如下:
public abstract class GodLeftHandBaseActivity extends GodBaseActivity implements View.OnClickListener {
protected TextView basetitle_tv;
protected ImageView baseback_img;
protected View basetop_view, godbase_view, basestatus_view;
@Override
protected void onGodCreate(Bundle savedInstanceState) {
setContentView(R.layout.activity_base);
resetStatusViewHeight();
initTopView();
init(savedInstanceState);
}
//初始化头布局
protected void initTopView() {
View view = LayoutInflater.from(this).inflate(setContentLayoutId(), null, false);
ViewGroup.LayoutParams layoutParams = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
view.setLayoutParams(layoutParams);
FrameLayout content_view = (FrameLayout) findViewById(.content_view);
content_view.addView(view);
basetop_view = findViewById(.basetop_view);
baseback_img = (ImageView) findViewById(.baseback_img);
basetitle_tv = (TextView) findViewById(.basetitle_tv);
godbase_view = findViewById(.godbase_view);
findViewById(.baseback_img).setOnClickListener(this);
}
//将状态栏高度赋给basestatus_view
private void resetStatusViewHeight() {
basestatus_view = findViewById(.basestatus_view);
int statusheight = getStatusBarHeight();
if (statusheight != -1) {
LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, statusheight);
basestatus_view.setLayoutParams(params);
}
}
protected abstract void init(Bundle savedInstanceState);
protected abstract int setContentLayoutId();
@Override
public void onClick(View v) {
}
}
接着我们把那个返回键的事件给它统一搞了,在onClick里面加上
if (v.getId() == .baseback_img) {
finish();
}
我们再回头看initTopView方法里面都实现了啥:
先解析出一个View
View view = LayoutInflater.from(this).inflate(setContentLayoutId(), null, false);
这View从我们其中一个抽象方法setContentLayoutId()中获取,然后把这个view添加到FrameLayout里面去,接着把头布局的一些控件初始化,再给头布局加点方法控制头布局一些操作
/
/设置标题
protected void setTitle(String title) {
basetitle_tv.setText(title);
}
//是否显示状态栏,默认显示
protected void showStatusView(boolean show) {
if (!show) basestatus_view.setVisibility(View.GONE);
else basestatus_view.setVisibility(View.VISIBLE);
}
//设置头布局状态栏背景颜色
protected void setTopViewBackgroundColor(int colorId) {
basetop_view.setBackgroundColor(colorId);
basestatus_view.setBackgroundColor(colorId);
}
//设置状态栏颜色
protected void setStatusBackgroundColor(int colorId) {
basestatus_view.setBackgroundColor(colorId);
}
//隐藏头布局
public void hideTopView() {
basetop_view.setVisibility(View.GONE);
basestatus_view.setVisibility(View.GONE);
}
//隐藏返回键
public void hideBackView() {
baseback_img.setVisibility(View.GONE);
}
接着到核心部分,把这个activity弄成ViewHolder模式创建一个private SparseArray<View> views = new SparseArray<>(); 一个view集合,它是拿来装我们内容布局子view的,再写一个getView方法:
public <T extends View> T getView(int viewId) {
View view = views.get(viewId);
if (view == null) {
view = findViewById(viewId);
views.put(viewId, view);
}
return (T) view;
}
和一些常用的View方法
protected TextView setText(int viewId, String text) {
TextView textView = getView(viewId);
textView.setText(text);
return textView;
}
protected TextView setText(int viewId, int res_id) {
TextView textView = getView(viewId);
textView.setText(getString(res_id));
return textView;
}
protected TextView setTextColor(int viewId, int colorId) {
TextView textView = getView(viewId);
textView.setTextColor(colorId);
return textView;
}
protected View setBackgroundColor(int viewId, int colorId) {
View view = getView(viewId);
view.setBackgroundColor(colorId);
return view;
}
等等等等...太多了我就不一一放 出来了,下面传送门会有完整的附上
还有一个点击事件不能忘!!我们再创建一个接口出来
public interface GodOnClickListener {
void OnClickListener(View view);
}
帮助我们实现点击事件,这时候又回到GodLeftHandBaseActivity中写一个setOnClickListener方法实现我们的点击事件
protected void setOnClickListener(GodOnClickListener godOnClickListener, int... viewIds) {
this.mGodOnClickListener = godOnClickListener;
for (int viewId : viewIds) {
View view = getView(viewId);
view.setOnClickListener(this);
}
}
接着在onClick中把这接口用上,此时的onClick方法如下:
@Override
public void onClick(View v) {
if (mGodOnClickListener != null) {
mGodOnClickListener.OnClickListener(v);
}
if (v.getId() == .baseback_img) {
finish();
}
}
至此暂告一段落,然后看看忙活了这么久这玩意到底有啥用吧!!
把我们的Activity继承GodLeftHandBaseActivity,然后如下图:
public class MainActivity extends GodLeftHandBaseActivity {
@Override
protected int setContentLayoutId() {
return 0;
}
@Override
protected void init(Bundle savedInstanceState) {
}
}
在setContentLayoutId方法中把我们这个activity的布局return回去就好了
@Override
protected int setContentLayoutId() {
return R.layout.activity_main;
}
这样,然后我们初始化的操作就在
@Override
protected void init(Bundle savedInstanceState) {
}
中进行,把它当onCreate来用就好,然后看看它的功能吧
比如一些其他的View比如自定义View和RecyclerView的操作:
左上角返回键的返回监听已经在父类处理掉了,所以我们不需要处理,当然我们还可以加一些自己顺手的很多功能,比如权限管理..
全部代码 github传送门:https:///poi13752/GodBaseActivity.git