闲话不多说,直接上图。
给大家讲讲我的编程思想吧。
第一部分:沉浸式状态栏(API-Level 19,AndroID4.4 KitKat 之后加入的东西),而且在API-Level 21版本中新增了一个属性(下面会说到)。所以,style文件应该声明三份。
values
<style name="Translucenttheme" parent="@style/Apptheme"></style>
values-19
<style name="Translucenttheme" parent="@style/Apptheme"> <item name="androID:windowTranslucentStatus">true</item> <item name="androID:windowTranslucentNavigation">false</item></style>
values-V21
<style name="Translucenttheme" parent="@style/Apptheme"> <item name="androID:windowTranslucentStatus">true</item> <item name="androID:windowTranslucentNavigation">false</item> <!-- v-21 中新增的属性 --> <item name="androID:statusbarcolor">@androID:color/transparent</item></style>
至于以上属性的含义及使用方式,就不多做解释了。详细可参见 https://www.oudahe.com/p/26557/
第二部分:actionbar渐变
因为要实现actionbar渐变,所以我没有使用系统的actionbar。而是自定义了一个继承自linearLayout的VIEwGroup。
直接给各位看代码
package test.com.Widget; import androID.content.Context; import androID.text.TextUtils; import androID.util.AttributeSet; import androID.vIEw.VIEw; import androID.vIEw.VIEwGroup; import androID.Widget.linearLayout; import androID.Widget.TextVIEw; import test.com.R; import test.com.impl.ActionbarClickListener; /** * 支持渐变的 actionbar * Created by 晖仔(Milo) on 2016/12/28. * email:303767416@qq.com */ public final class TranslucentActionbar extends linearLayout { private VIEw layRoot; private VIEw vstatusbar; private VIEw layleft; private VIEw layRight; public TextVIEw tvTitle; private TextVIEw tvleft; private TextVIEw tvRight; private VIEw iconleft; private VIEw iconRight; public TranslucentActionbar(Context context) { this(context,null); } public TranslucentActionbar(Context context,AttributeSet attrs) { super(context,attrs); init(); } public TranslucentActionbar(Context context,AttributeSet attrs,int defStyleAttr) { super(context,attrs,defStyleAttr); } private voID init() { setorIEntation(HORIZONTAL); VIEw contentVIEw = inflate(getContext(),R.layout.actionbar_trans,this); layRoot = contentVIEw.findVIEwByID(R.ID.lay_transroot); vstatusbar = contentVIEw.findVIEwByID(R.ID.v_statusbar); tvTitle = (TextVIEw) contentVIEw.findVIEwByID(R.ID.tv_actionbar_Title); tvleft = (TextVIEw) contentVIEw.findVIEwByID(R.ID.tv_actionbar_left); tvRight = (TextVIEw) contentVIEw.findVIEwByID(R.ID.tv_actionbar_right); iconleft = contentVIEw.findVIEwByID(R.ID.iv_actionbar_left); iconRight = contentVIEw.findVIEwByID(R.ID.v_actionbar_right); } /** * 设置状态栏高度 * * @param statusbarHeight */ public voID setStatusbarHeight(int statusbarHeight) { VIEwGroup.LayoutParams params = vstatusbar.getLayoutParams(); params.height = statusbarHeight; vstatusbar.setLayoutParams(params); } /** * 设置是否需要渐变 */ public voID setNeedTranslucent() { setNeedTranslucent(true,false); } /** * 设置是否需要渐变,并且隐藏标题 * * @param translucent */ public voID setNeedTranslucent(boolean translucent,boolean TitleInitVisibile) { if (translucent) { layRoot.setBackgroundDrawable(null); } if (!TitleInitVisibile) { tvTitle.setVisibility(VIEw.GONE); } } /** * 设置标题 * * @param strTitle */ public voID setTitle(String strTitle) { if (!TextUtils.isEmpty(strTitle)) { tvTitle.setText(strTitle); } else { tvTitle.setVisibility(VIEw.GONE); } } /** * 设置数据 * * @param strTitle * @param resIDleft * @param strleft * @param resIDRight * @param strRight * @param Listener */ public voID setData(String strTitle,int resIDleft,String strleft,int resIDRight,String strRight,final ActionbarClickListener Listener) { if (!TextUtils.isEmpty(strTitle)) { tvTitle.setText(strTitle); } else { tvTitle.setVisibility(VIEw.GONE); } if (!TextUtils.isEmpty(strleft)) { tvleft.setText(strleft); tvleft.setVisibility(VIEw.VISIBLE); } else { tvleft.setVisibility(VIEw.GONE); } if (!TextUtils.isEmpty(strRight)) { tvRight.setText(strRight); tvRight.setVisibility(VIEw.VISIBLE); } else { tvRight.setVisibility(VIEw.GONE); } if (resIDleft == 0) { iconleft.setVisibility(VIEw.GONE); } else { iconleft.setBackgroundResource(resIDleft); iconleft.setVisibility(VIEw.VISIBLE); } if (resIDRight == 0) { iconRight.setVisibility(VIEw.GONE); } else { iconRight.setBackgroundResource(resIDRight); iconRight.setVisibility(VIEw.VISIBLE); } if (Listener != null) { layleft = findVIEwByID(R.ID.lay_actionbar_left); layRight = findVIEwByID(R.ID.lay_actionbar_right); layleft.setonClickListener(new VIEw.OnClickListener() { @OverrIDe public voID onClick(VIEw v) { Listener.onleftClick(); } }); layRight.setonClickListener(new VIEw.OnClickListener() { @OverrIDe public voID onClick(VIEw v) { Listener.onRightClick(); } }); } } }
下面是actionbar_trans.xml的代码
<?xml version="1.0" enCoding="utf-8"?> <linearLayout xmlns:androID="http://schemas.androID.com/apk/res/androID" androID:ID="@+ID/lay_transroot" androID:layout_wIDth="match_parent" androID:layout_height="wrap_content" androID:background="@color/colorPrimary" androID:orIEntation="vertical"> <VIEw androID:ID="@+ID/v_statusbar" androID:layout_wIDth="match_parent" androID:layout_height="1.0dp" /> <relativeLayout androID:layout_wIDth="match_parent" androID:layout_height="45dp" androID:orIEntation="vertical"> <relativeLayout androID:ID="@+ID/lay_actionbar_left" androID:layout_wIDth="100dp" androID:layout_height="match_parent" androID:orIEntation="horizontal"> <ImageVIEw androID:ID="@+ID/iv_actionbar_left" androID:layout_wIDth="20dp" androID:layout_height="20dp" androID:layout_centerVertical="true" androID:layout_marginleft="10dp" androID:background="@mipmap/ic_left_light" androID:visibility="gone" /> <TextVIEw androID:ID="@+ID/tv_actionbar_left" androID:layout_height="match_parent" androID:layout_marginleft="10dp" androID:layout_toRightOf="@+ID/iv_actionbar_left" androID:gravity="center_vertical" androID:maxLength="2" androID:singleline="true" androID:text="返回" androID:visibility="gone" /> </relativeLayout> <TextVIEw androID:ID="@+ID/tv_actionbar_Title" androID:layout_centerInParent="true" androID:text="标题" androID:textSize="16sp" /> <relativeLayout androID:ID="@+ID/lay_actionbar_right" androID:layout_wIDth="100dp" androID:layout_height="match_parent" androID:layout_alignParentRight="true" androID:gravity="right" androID:orIEntation="horizontal"> <VIEw androID:ID="@+ID/v_actionbar_right" androID:layout_wIDth="20dp" androID:layout_height="20dp" androID:layout_alignParentRight="true" androID:layout_centerVertical="true" androID:layout_marginRight="10dp" androID:visibility="gone" /> <TextVIEw androID:ID="@+ID/tv_actionbar_right" androID:layout_height="match_parent" androID:layout_marginRight="10dp" androID:layout_toleftOf="@+ID/v_actionbar_right" androID:gravity="center_vertical|right" androID:singleline="true" androID:visibility="gone" /> </relativeLayout> </relativeLayout> </linearLayout>
这里我即没有用到 androID:fitsSystemwindows="true" 属性,也没有用到 StatusbarUtils ,因为我发现使用的时候很容易造成兼容问题。
所以,我的做法是声明了一个高度为0.0dp的 statusbar,背景为透明,然后获取状态栏高度并赋值到它上,来实现兼容。事实证明,这样做的兼容效果最好。
获取状态栏高度代码:
/** * 获取状态栏高度 * * @return */ public int getStatusbarHeight() { //获取status_bar_height资源的ID int resourceID = getResources().getIDentifIEr("status_bar_height","dimen","androID"); if (resourceID > 0) { //根据资源ID获取响应的尺寸值 return getResources().getDimensionPixelSize(resourceID); } return 0; }
设置 statusbar高度:
/** * 设置状态栏高度 * * @param statusbarHeight */ public voID setStatusbarHeight(int statusbarHeight) { VIEwGroup.LayoutParams params = vstatusbar.getLayoutParams(); params.height = statusbarHeight; vstatusbar.setLayoutParams(params); }
开启渐变:
/** * 设置是否需要渐变 */ public voID setNeedTranslucent() { setNeedTranslucent(true,false); } /** * 设置是否需要渐变,并且隐藏标题 * * @param translucent */ public voID setNeedTranslucent(boolean translucent,boolean TitleInitVisibile) { if (translucent) { layRoot.setBackgroundDrawable(null); } if (!TitleInitVisibile) { tvTitle.setVisibility(VIEw.GONE); } }
第三步:实现ScrollVIEw顶部伸缩
到了这里,必须得说一下,因为是个人项目中用到,所以并没有把功能做的很强大,本人都是以最简单、有效的方式实现的。所以,代码并不像gitHub上那些被下载很多次的开源项目一样,有很高的扩展性。
时间关系,我直接贴代码吧,代码里我都写了注释的。
package test.com.Widget; import androID.animation.ObjectAnimator; import androID.animation.ValueAnimator; import androID.content.Context; import androID.graphics.color; import androID.support.annotation.colorInt; import androID.support.v4.graphics.colorUtils; import androID.util.AttributeSet; import androID.util.Log; import androID.vIEw.MotionEvent; import androID.vIEw.VIEw; import androID.vIEw.VIEwGroup; import androID.vIEw.WindowManager; import androID.Widget.ScrollVIEw; import test.com.R; import test.com.utils.SizeUtils; /** * Created by 晖仔(Milo) on 2017/2/13. * email:303767416@qq.com */ public class TranslucentScrollVIEw extends ScrollVIEw { static final String TAG = "TranslucentScrollVIEw"; //伸缩视图 private VIEw zoomVIEw; //伸缩视图初始高度 private int zoomVIEwInitHeight = 0; // 记录首次按下位置 private float mFirstposition = 0; // 是否正在放大 private Boolean mScaling = false; //渐变的视图 private VIEw transVIEw; //渐变颜色 private int transcolor = color.WHITE; //渐变开始位置 private int transstartY = 50; //渐变结束位置 private int transEndY = 300; //渐变开始默认位置,Y轴,50dp private final int DFT_TRANsstARTY = 50; //渐变结束默认位置,Y轴,300dp private final int DFT_TRANSENDY = 300; private TranslucentScrollVIEw.TranslucentChangedListener translucentChangedListener; public interface TranslucentChangedListener { /** * 透明度变化,取值范围0-255 * * @param transAlpha */ voID onTranslucentChanged(int transAlpha); } public TranslucentScrollVIEw(Context context) { super(context); } public TranslucentScrollVIEw(Context context,attrs); } public TranslucentScrollVIEw(Context context,defStyleAttr); } public voID setTranslucentChangedListener(TranslucentScrollVIEw.TranslucentChangedListener translucentChangedListener) { this.translucentChangedListener = translucentChangedListener; } /** * 设置伸缩视图 * * @param zoomVIEw */ public voID setPullZoomVIEw(VIEw zoomVIEw) { this.zoomVIEw = zoomVIEw; zoomVIEwInitHeight = zoomVIEw.getLayoutParams().height; if (zoomVIEwInitHeight == LayoutParams.MATCH_PARENT || zoomVIEwInitHeight == WindowManager.LayoutParams.WRAP_CONTENT) { zoomVIEw.post(new Runnable() { @OverrIDe public voID run() { zoomVIEwInitHeight = TranslucentScrollVIEw.this.zoomVIEw.getHeight(); } }); } } /** * 设置渐变视图 * * @param transVIEw 渐变的视图 */ public voID setTransVIEw(VIEw transVIEw) { setTransVIEw(transVIEw,getResources().getcolor(R.color.colorPrimary),SizeUtils.dip2px(getContext(),DFT_TRANsstARTY),DFT_TRANSENDY)); } /** * 设置渐变视图 * * @param transVIEw 渐变的视图 * @param transcolor 渐变颜色 * @param transEndY 渐变结束位置 */ public voID setTransVIEw(VIEw transVIEw,@colorInt int transcolor,int transstartY,int transEndY) { this.transVIEw = transVIEw; //初始视图-透明 this.transVIEw.setBackgroundcolor(colorUtils.setAlphaComponent(transcolor,0)); this.transstartY = transstartY; this.transEndY = transEndY; this.transcolor = transcolor; if (transstartY > transEndY) { throw new IllegalArgumentException("transstartY 不得大于 transEndY .. "); } } /** * 获取透明度 * * @return */ private int getTransAlpha() { float scrollY = getScrollY(); if (transstartY != 0) { if (scrollY <= transstartY) { return 0; } else if (scrollY >= transEndY) { return 255; } else { return (int) ((scrollY - transstartY) / (transEndY - transstartY) * 255); } } else { if (scrollY >= transEndY) { return 255; } return (int) ((transEndY - scrollY) / transEndY * 255); } } /** * 重置ZoomVIEw */ private voID resetZoomVIEw() { final VIEwGroup.LayoutParams lp = zoomVIEw.getLayoutParams(); final float h = zoomVIEw.getLayoutParams().height;// ZoomVIEw当前高度 // 设置动画 ValueAnimator anim = ObjectAnimator.offloat(0.0F,1.0F).setDuration(200); anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @OverrIDe public voID onAnimationUpdate(ValueAnimator animation) { float cVal = (float) animation.getAnimatedValue(); lp.height = (int) (h - (h - zoomVIEwInitHeight) * cVal); zoomVIEw.setLayoutParams(lp); } }); anim.start(); } @OverrIDe protected voID onScrollChanged(int l,int t,int oldl,int oldt) { super.onScrollChanged(l,t,oldl,oldt); int transAlpha = getTransAlpha(); if (transVIEw != null) { Log.d(TAG,"[onScrollChanged .. in ],透明度 == " + transAlpha); transVIEw.setBackgroundcolor(colorUtils.setAlphaComponent(transcolor,transAlpha)); } if (translucentChangedListener != null) { translucentChangedListener.onTranslucentChanged(transAlpha); } } @OverrIDe public boolean ontouchEvent(MotionEvent event) { if (zoomVIEw != null) { VIEwGroup.LayoutParams params = zoomVIEw.getLayoutParams(); switch (event.getAction()) { case MotionEvent.ACTION_UP: //手指离开后恢复图片 mScaling = false; resetZoomVIEw(); break; case MotionEvent.ACTION_MOVE: if (!mScaling) { if (getScrollY() == 0) { mFirstposition = event.getY(); } else { break; } } int distance = (int) ((event.getY() - mFirstposition) * 0.6); if (distance < 0) { break; } mScaling = true; params.height = zoomVIEwInitHeight + distance; Log.d(TAG,"params.height == " + params.height + ",zoomVIEwInitHeight == " + zoomVIEwInitHeight + ",distance == " + distance); zoomVIEw.setLayoutParams(params); return true; } } return super.ontouchEvent(event); } }
总结
以上所述是小编给大家介绍的AndroID沉浸式状态栏 + actionbar渐变 + scrollVIEw顶部伸缩,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对编程小技巧网站的支持!
总结以上是内存溢出为你收集整理的Android沉浸式状态栏 + actionBar渐变 + scrollView顶部伸缩效果全部内容,希望文章能够帮你解决Android沉浸式状态栏 + actionBar渐变 + scrollView顶部伸缩效果所遇到的程序开发问题。
如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)