Android 몰입 형 상태 표시 줄+actionBar 그 라 데 이 션+scrollView 상단 신축 효과
제 프로 그래 밍 사상 을 말씀 드 리 겠 습 니 다.
첫 번 째 부분:몰입 형 상태 표시 줄(API-Level 19,Android 4.4 KitKat 이후 추 가 된 것),그리고 API-Level 21 버 전에 속성 이 추가 되 었 습 니 다.그래서 스타일 파일 은 세 부 를 설명해 야 합 니 다.
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.jb51.net/article/104485.htm두 번 째 부분:actionBar 그 라 데 이 션
actionBar 그 라 데 이 션 을 실현 해 야 하기 때문에 시스템 의 actionBar 를 사용 하지 않 았 습 니 다.LinearLayout 에서 계승 할 View Group 을 사용자 정의 한 것 입 니 다.
코드 를 바로 보 여 드릴 게 요.
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:[email protected]
*/
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();
}
});
}
}
}
다음은 actionbartrans.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"
style="@style/text_white"
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"
style="@style/text_white"
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"
style="@style/text_white"
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>
여기 서 저 는 안 드 로 이 드:fitsSystem Windows="true"속성 을 사용 하지 않 았 고 StatusBarUtils 도 사용 하지 않 았 습 니 다.사용 할 때 호 환 문제 가 발생 하기 쉽다 는 것 을 알 았 기 때 문 입 니 다.그래서 제 방법 은 0.0dp 높이 의 status bar 를 설명 한 다음 에 상태 표시 줄 높이 를 가 져 와 서 호 환 을 실현 하 는 것 입 니 다.사실은 이렇게 하 는 호환성 이 가장 좋다 는 것 을 증명 한다.
상태 표시 줄 높이 코드 가 져 오기:
/**
*
*
* @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;
}
status bar 높이 설정:
/**
*
*
* @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);
}
}
STEP 3: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:[email protected]
*/
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, AttributeSet attrs) {
super(context, attrs);
}
public TranslucentScrollView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, 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), SizeUtils.dip2px(getContext(), 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);
}
}
총결산위 에서 말 한 것 은 소 편 이 소개 한 안 드 로 이 드 몰입 식 상태 표시 줄+actionBar 그 라 데 이 션+scrollView 상단 신축 입 니 다.도움 이 되 셨 으 면 좋 겠 습 니 다.궁금 한 점 이 있 으 시 면 메 시 지 를 남 겨 주세요.소 편 은 바로 답 해 드 리 겠 습 니 다.여기 서도 저희 사이트 에 대한 여러분 의 지지 에 감 사 드 립 니 다!
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Kotlin의 기초 - 2부지난 글에서는 Kotlin이 무엇인지, Kotlin의 특징, Kotlin에서 변수 및 데이터 유형을 선언하는 방법과 같은 Kotlin의 기본 개념에 대해 배웠습니다. 유형 변환은 데이터 변수의 한 유형을 다른 데이터...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.